arraylist的副本不断修改为原始值

我正在研究一个用于保存和调用屏幕状态的系统,这是我第一次搞乱这种东西,所以我不确定最好的方法是什么,但我目前存储所有的“PreviewMonitor”数组列表中的对象(大约40个左右)。 问题在于,当我创建一个名为“allPreviewMonitors”的ArrayList副本时,我最终得到一个ArrayList,其元素随着原始元素的更新而不断变化。 这几乎就像我正在使用原始的ArrayList,事实上,当我创建allPreviewMonitors的副本时,它应该是一个完全不同的ArrayList,其中包含元素的“冻结”版本及其状态。 为什么会发生这种情况? 如果需要我可以显示代码,但我不确定这里是否需要它。

您只是将对象引用复制到ArrayList中。 您需要自己复制对象。

在Java中,所有对象变量实际上都是引用变量。 所以代码:

Myclass myObject = new Myclass(); Myclass otherObject = myObject; 

创建一个Myclass对象,并在引用变量myObject存储对该Myclass对象的引用。 然后,它创建一个新的引用变量otherObject ,并将引用数据(例如,内存地址)从myObject复制到otherObject 。 这些现在引用内存中的相同对象。 此时,行

 myObject.myMethod(); 

与…有相同的结果

 otherObject.myMethod(); 

您在ArrayList中获得的是对相同对象的不同引用。 你想要的是以下之一:

 Myclass otherObject = myObject.clone(); // use the clone function // OR Myclass otherObject = new Myclass(myObject); // use a copy constructor 

如果使用clone()或复制构造函数将对象放入ArrayList,则ArrayList将包含对相同副本的引用,而不是对相同副本的引用。

正如其他人所指出的那样,只是制作引用的副本称为“浅拷贝”,而将所引用的对象的副本称为“深拷贝”

像所有Collections一样的Arraylist只包含对象的引用。 复制List是不够的,您还必须在创建List副本时克隆()元素(或创建新元素,或使用复制构造函数)。

这称为“深拷贝”,而您目前有“浅拷贝”。

您需要确保执行“深层复制” – 即克隆PreviewMonitor对象。 默认情况下,您只需执行浅拷贝并复制对同一对象的引用。

要克隆,您不能只返回当前对象。 您必须使用与当前对象相同的值创建新对象。 换句话说,使用当前对象的Class的构造函数并创建一个新对象。 确保旧对象和新对象之间的属性匹配。 返回新对象并对原始列表中的每个对象重复。