【问题标题】:Need some clarification about reference type's behavior需要澄清一下引用类型的行为
【发布时间】:2019-05-10 11:19:27
【问题描述】:

我看过Difference between a Value Type and a Reference Type,在这篇文章中,作者是说:

因为引用类型代表变量的地址而不是数据本身,所以将引用变量分配给另一个不会复制数据。相反,它会创建引用的第二个副本,它引用与原始值相同的堆位置

基于上面的引用,我预计下面的代码会将引用变量分配给另一个变量,它不会复制数据,但它确实也在复制数据。你能帮我理解一下吗?

Class1 i1 = new Class1();
i1.Name = "Name1";
Class1 i2 = i1;
//i2.Name is "Name1"

对于i2,我希望它指的是与i1 值相同的堆位置,这是正确的,但根据文章,不应复制数据。另外,我的问题不应该被标记为重复,因为我知道值和引用类型之间的区别,我只需要澄清一下引用类型以及深拷贝/克隆/浅层的用法,如果我们可以简单地使用赋值?

【问题讨论】:

  • 但它不会复制任何东西。 i1i2 都指向同一个对象
  • @Fabjan 那么为什么i2.NameName1。这不是从i1复制过来的吗?
  • 仅仅因为有人将您的电话号码从您的名片复制到记事本中,并不意味着您突然有了一个双胞胎。你不会被复制。仅复制了对您的引用(书面电话号码)。
  • 因为它指向 same 对象所以值是相同的
  • 它们之间的唯一区别是引用的名称。

标签: c# oop reference-type


【解决方案1】:

对于 i2,我预计它指的是与 i1 相同的堆位置 正确的价值观

正确,它们指向内存中的相同位置。

但根据文章,数据不应被复制。

再次纠正,数据不是复制的,我们一起来看看:

             _ _ _ _
            |       |
 i1  - - - -| addr  |
            |_ _ _ _|

现在,当您执行 Class1 i2 = i1; 时,您实际上是在复制 i1 的引用并将其分配给 i2,您可以将其可视化为:

             _ _ _ _
            |       |
 i1  - - - -| addr  |
            |_ _ _ _|
          /
         /               
        /     
   i2  /

因此i1.Namei2.Name 具有相同的名称,因为i1i2 引用内存中的同一个对象。

【讨论】:

【解决方案2】:

引用只是一个指向对象的指针。这样做只是复制参考。如果你这样做了i2.Name = "foobar";i1.Name也会变成foobar

【讨论】:

    猜你喜欢
    • 2017-01-18
    • 2021-07-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-09-06
    • 1970-01-01
    相关资源
    最近更新 更多