C# 对象复制说明
本文关键字:说明 复制 对象 | 更新日期: 2023-09-27 18:35:36
在我开始之前,我知道还有其他几个问题可以"回答"这个问题,但不是我能完全理解的方式。这就是我所指的:C# 中的深度复制
为什么在 C# 中复制是一个糟糕的主意
我做了相当多的研究,我希望有人能向我解释如何将对象设置为另一个对象的值。
例如,假设:
myObject bob;
bob = new myObject();
myObject joe
joe = bob
根据我的研究,joe
现在指向鲍勃的bob
实例。这些对象是否仍独立运行?
我将如何创建两个对象,将一个对象的内容复制到另一个对象,并使它们成为两个单独的对象,其字段、方法和事件分别发生?
我很抱歉再次问这个问题,但我似乎在其他任何地方都找不到对我有意义的解释。
它们都指向同一个实例。如果需要两个单独的实例,请使用 new
运算符创建第二个实例。
让我们浏览每一行:
myObject bob; // Creates a variable of type myObject, but it doesn't point anywhere
bob = new myObject(); // bob now points to a newly created myObject instance
myObject joe; // Creates a variable of type myObject, but it doesn't point anywhere
joe = bob; // joe now refers to the same object as bob
要记住的重要一点是,最后一行复制引用本身的值。 例如,如果bob
指向地址 1000,joe
也会指向那里。 因此,如果您更改此地址的任何数据,joe
和 bob
都将指向相同的数据。
但是,欢迎您将joe
设置为指向其他地方,这不会影响bob
。 换句话说:
joe = null; // This will not null out bob
如果你想创建一个全新的myObject
实例,你必须这样做:
joe = new myObject(); // This will also not affect bob
现在,如果您尝试在内存中创建myObject
的新实例并复制现有实例的所有属性,则必须自己执行此操作:
joe = new myObject();
joe.X = bob.X; // Assuming X is not a reference itself
joe.Y = bob.Y; // ...or you'd have to do this recursively
.NET 不提供执行此操作复制的方法。 一种常见的模式是为myObject()
创建一个构造函数,该构造函数采用myObject
实例并复制其所有属性:
joe = new myObject(bob);
是的,bob
和 joe
都指向那里完全相同的对象。
对象的复制确实需要基于每个类来完成。假设您有一个只有值类型的类(可能是一些整数和字符串)。复制其中的每个字段都可以正常工作。
但是现在想象一下,如果你的类包含对其他对象的引用(这很可能),如果你只是逐个字段复制这个对象,你现在将有两个不同的实例共享一些数据(一个打开的文件,一个网络套接字等)。因此,要可靠地复制对象,您应该让该对象创建自身的副本,因为它知道它包含哪种数据。
所以答案是,在 C# 中没有安全的通用方法来复制对象。
您在这里将数据与方法混淆了。数据定义对象是什么。例如radius
2 的 A circle
。方法作用于该数据,例如IncreaseRadius()
当您复制时,将复制此数据,而不是方法。方法只对类数据进行操作,并生成特定于类数据的输出。
不。它们都指向同一个对象。 bob
和 joe
只是 2 个变量,它们在内存中保存对同一对象的引用。如果您通过bob
更改数据并从joe
中读取,您将获得新的值。
标准方法是实现ICloneable
接口并使用它来创建深层副本。我的意思是您必须在方法中创建一个新对象Clone
并将每个数据成员复制到新创建的对象。如果数据是另一种引用类型,那么您也必须克隆它。