我觉得这很无知,但是有人能够向我解释为什么会这样吗?
class MyClass{ public int i {get; set; } } class Program { static void Main(string[] args) { MyClass a = new MyClass(); MyClass b = new MyClass(); b.i = 2; a = b; a.i = 1; Console.Write(b.i + "\n"); //Outputs 1 } }
这对我来说是有道理的,因为我使用指针和所有那些伟大的东西,但我的印象是,使用C#,“b”将保持独立于“a”。
我只是使用了一些非常糟糕的做法吗?也许有人可以指点我解释为什么在C#中会出现这种情况?
感谢。
答案 0 :(得分:10)
这条线让你感到困惑:
a = b;
您希望b
按值复制到a
,但事实上,您已将b
的引用分配给a
。
.Net将世界划分为两类:引用类型和值类型(还有委托类型和其他几个,但这是另一个故事)。您定义的任何类都是引用类型,并且有一些重要的事项要记住引用类型:
.Equals()
用于值相等,您可能需要覆盖.Equals()(和GetHashCode( ))为你的类型做到这一点。答案 1 :(得分:4)
答案 2 :(得分:2)
您需要了解的情况是,实际上有4个感兴趣的实体。
最初引用a引用实例#1,引用b引用实例#2。这是在你执行第a=b;
行之前。在此行之后,两者都引用a和引用b指向实例#1。因此,当您致电b.i
时,您实际上是在询问实例#1,i
的值是多少。不是实例#2。
答案 3 :(得分:1)
没有指针与没有引用对象不同。在您的情况下,'a'是对MyClass类型的特定对象的引用,以及'b'。当您执行'a = b'时,您正在复制引用,而不是对象,因此'a'指向与'b'相同的对象。
答案 4 :(得分:0)
a和b是引用,因此在行a = b
之后,a引用与b相同的对象(并且最初由a指向的对象不再可访问)。因此,当您设置a.i
时,您还要更新b引用的对象,因此更改。
答案 5 :(得分:0)
.NET中的每个类都是引用类型。这意味着当您创建新实例时,它指向内存中的引用而不保持其值。
在您的情况下,当您使用a
(赋值)时,您只需将对象b
的指针与对象# printf to a variable (psql_array) replacing single quotes by two single quotes
printf -v psql_array "'%s'," "${ARRVAR[@]//\'/\'\'}"
# remove the trailing ,
psql_array=${psql_array%,}
# check
echo "($psql_array)"
# or to have a postgresql varchar[]
# escape double quote between double quotes
printf -v psql_array "\"%s\"," "${ARRVAR[@]//\"/\\\"}"
psql_array=${psql_array%,}
echo "{$psql_array}"
# or easier
printf -v psql_array "'%s'::varchar," "${ARRVAR[@]//\'/\'\'}"
echo "ARRAY[${psql_array%,}]"
的指针相关联。在此操作之后,对象上的每个交互都将反映给其他人,因为他们只是指向同一个事物。
如果需要复制对象,则必须自己编写代码。但这是另一个故事。