您只是将对象引用复制到您的 ArrayList 中。您需要自己复制对象。
在Java中,所有的对象变量实际上都是引用变量。所以代码:
Myclass myObject = new Myclass();
Myclass otherObject = myObject;
创建一个 Myclass 对象并将对该 Myclass 对象的引用存储在引用变量myObject 中。然后它创建一个新的引用变量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 将包含对相同副本的引用,而不是对相同副本的引用。
正如其他人所指出的,仅制作引用的副本称为“浅拷贝”,而制作引用的对象的副本称为“深拷贝”。
编辑:为了使它起作用,您的解决方案不仅要在你的类上实现,而且要在你的类中包含的所有类上实现。例如,考虑MyClass,它的字段类型为OtherClass:
class MyClass {
private String foo;
private OtherClass bar;
private int x;
MyClass(String f, OtherClass b, int x) {
foo = f;
bar = b;
this.x = x;
}
MyClass(MyClass o) {
//make sure to call the copy constructor of OtherClass
this(new String(o.foo), new OtherClass(o.bar), o.x);
}
// getters and setters
}
请注意,这需要OtherClass 也有一个复制构造函数!如果OtherClass 引用其他类,那么它们也需要复制构造函数。没有办法。
最后,您的列表副本将如下所示:
List<MyClass> myNewList = new ArrayList<>(myExistingList.size());
for ( MyClass item : myExistingList) {
// use the copy constructor of MyClass, which uses the copy constructor of OtherClass, etc, etc.
myNewList.add(new MyClass(item))
}