Типы значений и ссылочные типы
Переменная xStr - ссылочный тип или нет ?
Почему переменную xStr - не затрагивают изменения как объект stringBuilder ?
В метод всё таки попадает копия значения, а не копия ссылки ?
class Program
{
static void Main(string[] args)
{
int xInt = 0;
string xStr = "0";
StringBuilder stringBuilder = new("0");
TestChange(xInt);
TestChange(xStr);
TestChange(stringBuilder);
Console.WriteLine(xInt);
Console.WriteLine(xStr);
Console.WriteLine(stringBuilder);
}
static void TestChange(int xInt)
{
xInt = 1;
}
static void TestChange(string xStr)
{
xStr = "1";
}
static void TestChange(StringBuilder stringBuilder)
{
stringBuilder.Clear();
stringBuilder.Append("1");
}
}
В консоли вывод:
0
0
1
UPD
class Program
{
static void Main(string[] args)
{
int xInt = 0;
string xStr = "0";
StringBuilder stringBuilder = new("0");
TestChange(xInt);
TestChange(xStr);
TestChange(stringBuilder);
Console.WriteLine(xInt);
Console.WriteLine(xStr);
Console.WriteLine(stringBuilder);
}
static void TestChange(int xInt)
{
xInt = 1;
}
static void TestChange(string xStr)
{
xStr = null;
}
static void TestChange(StringBuilder stringBuilder)
{
stringBuilder = null;
}
}
В консоли вывод:
0
0
0
UPD: Разобрался в понимании - спасибо!
Ответы (3 шт):
В языке C# тип String является неизменяемым. Это означает, что, когда вы присваиваете одной переменной новое значение, то создаётся новый объект типа String и сохраняется в этой пременной, а прежний объект теряется, если на него не указывают другие ссылки.
Подумайте о разнице между
variable = another_value;
и
variable.modifyVariableContent();
внутри функции, куда передается variable.
Чтобы Int менялся, его надо по ссылке передавать, а не по значению:
static void TestChange(ref int xInt)
{
xInt = 1;
}
Иначе создаётся локальная переменная типа int в функции. Согласно ответу @SergeyK, со стрингами та же история.
using NUnit.Framework;
[Test]
public static void Test()
{
int xInt = 1;
string xStr = "1";
StringBuilder stringBuilder = new("1");
TestChange(ref xInt);
TestChange(ref xStr);
TestChange(ref stringBuilder);
Console.WriteLine(xInt);
Console.WriteLine(xStr);
Console.WriteLine(stringBuilder);
}
static void TestChange<T>(ref T value)
{
dynamic d = null;
if (typeof(string) == typeof(T))
d = "0";
else if (typeof(int) == typeof(T))
d = 0;
else if (typeof(StringBuilder) == typeof(T))
d = new StringBuilder("0");
value = d;
}
Standard Output: 0 0 0