Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/372.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java不安全或未检查的表达式:克隆arraylist_Java_Compiler Errors_Type Safety - Fatal编程技术网

Java不安全或未检查的表达式:克隆arraylist

Java不安全或未检查的表达式:克隆arraylist,java,compiler-errors,type-safety,Java,Compiler Errors,Type Safety,我在编译时遇到了未检查的表达式错误,发现有问题的行是 ArrayList<Integer> items = (ArrayList<Integer>) this.items.clone(); 我正在尝试执行对象的深度复制,因此我正在以上述方式克隆对象和数组列表的属性。如何修复此警告 我可以使用@SuppressWarningUnchecked,但这只是隐藏了问题,而我不希望出现任何问题 如果我通过循环所有元素来手动克隆,我认为会更慢 正确的方法是什么?使用新的ArrayL

我在编译时遇到了未检查的表达式错误,发现有问题的行是

ArrayList<Integer> items = (ArrayList<Integer>) this.items.clone();
我正在尝试执行对象的深度复制,因此我正在以上述方式克隆对象和数组列表的属性。如何修复此警告

我可以使用@SuppressWarningUnchecked,但这只是隐藏了问题,而我不希望出现任何问题 如果我通过循环所有元素来手动克隆,我认为会更慢
正确的方法是什么?

使用新的ArrayListthis.items可以获得相同的行为。不管怎样,这都是肤浅的复制品


您可以使用新的ArrayListthis.items获得相同的行为。不管怎样,这都是肤浅的复制品


由于在Java API中引入泛型时需要向后兼容,因此在某些情况下无法使用强制转换和@SuppressWarningUnchecked


另外,请参阅了解为什么使用克隆时要小心:它会进行浅拷贝,这对灵长类来说很好,但对对象来说很危险。

由于在Java API中引入泛型时需要向后兼容,因此在某些情况下无法使用强制转换和@suppressWarningUnchecked


另外,请参阅了解为什么使用克隆时要小心:它可以进行浅拷贝,这对灵长类动物来说是好的,但对对象来说是危险的。

您说过您正在尝试进行深度拷贝,但正如前面所讨论的,我怀疑您是否能够使用克隆来实现这一点。因此,正如其他海报所说,使用克隆是一种更危险的方法,您将无法获得您一直在寻找的深度拷贝。

您说过您正在尝试进行深度拷贝,但正如前面所讨论的,我怀疑您能否使用克隆来实现这一点。因此,正如其他海报所说,使用克隆是一种更危险的方法,您将无法获得您一直在寻找的深度副本。

如果您的元素是整数,则执行深度副本实际上不是问题,因为您没有理由需要复制整数对象。只需使用新的ArrayListthis.items


但作为参考,克隆和ArrayList复制构造函数都不会执行深度复制。这只是因为您的元素类型不需要深度复制,这就满足了您的需要。

如果您的元素是整数,执行深度复制实际上不是问题,因为没有理由需要复制整数对象。只需使用新的ArrayListthis.items


但作为参考,克隆和ArrayList复制构造函数都不会执行深度复制。只是因为您的元素类型不需要深度复制,这才满足了您的需要。

整数是不可变的,所以是否进行深度复制无关紧要

使用java.util中的Collections实用程序类:

import java.util.Collections;
...
ArrayList<Integer> items = new ArrayList<Integer>(this.items.size());
Collections.copy(items, this.items);

整数是不可变的,所以是否进行深度复制并不重要

使用java.util中的Collections实用程序类:

import java.util.Collections;
...
ArrayList<Integer> items = new ArrayList<Integer>(this.items.size());
Collections.copy(items, this.items);

正如其他人指出的那样,克隆ArrayList并不克隆其元素。如果您想制作内容的深度副本,有一个巧妙的技巧:序列化和反序列化数组。这是因为ArrayList和Integer都实现了可序列化。但是,这并不能消除抑制未检查的转换警告的需要

// Write the object out to a byte array
ByteArrayOutputStream bos = new ByteArrayOutputStream();
ObjectOutputStream out = new ObjectOutputStream(bos);
out.writeObject(this.items);
byte[] bytes = bos.toByteArray();

// Retrieve an input stream from the byte array and read
// a copy of the object back in.
ObjectInputStream in = new ObjectInputStream(
    new ByteArrayInputStream(bytes));
ArrayList<Integer> items = (ArrayList<Integer>) in.readObject();

如果可以将整个对象声明为可序列化,则可以使用此操作而不是克隆操作来创建深度副本。另外,请参阅以获取避免从ByteArrayOutput流中复制字节的方法。

正如其他人所指出的,克隆ArrayList不会克隆其元素。如果您想制作内容的深度副本,有一个巧妙的技巧:序列化和反序列化数组。这是因为ArrayList和Integer都实现了可序列化。但是,这并不能消除抑制未检查的转换警告的需要

// Write the object out to a byte array
ByteArrayOutputStream bos = new ByteArrayOutputStream();
ObjectOutputStream out = new ObjectOutputStream(bos);
out.writeObject(this.items);
byte[] bytes = bos.toByteArray();

// Retrieve an input stream from the byte array and read
// a copy of the object back in.
ObjectInputStream in = new ObjectInputStream(
    new ByteArrayInputStream(bytes));
ArrayList<Integer> items = (ArrayList<Integer>) in.readObject();

如果可以将整个对象声明为可序列化,则可以使用此操作而不是克隆操作来创建深度副本。另外,请参阅,了解避免从ByteArrayOutputStream复制字节的方法。

可以将原语放入ArrayList中吗?我以为你只能放对象,最多只能放原语的包装器。@blahman重点是原语字段在克隆时是可以的,但是像ArrayList项这样的对象字段是麻烦的来源。哦……哎呀。完全错过了。对不起,Yuushi。我的错^^同样,谢谢@TedHopp=您可以在ArrayList中放置原语吗?我以为你只能放对象,最多只能放原语的包装器。@blahman重点是原语字段在克隆时是可以的,但是像ArrayList项这样的对象字段是麻烦的来源。哦……哎呀。完全错过了。对不起,Yuushi。我的坏^^也感谢@TedHopp=当然,没有必要制作整数对象的深度副本。当然,没有必要制作整数对象的深度副本。Arrays.copyOf不返回a
rrayList.Oops表示Collections.copy,而不是Arrays.copyOf.Arrays.copyOf不返回ArrayList.Oops表示Collections.copy,而不是Arrays.copyOf。