【发布时间】:2014-03-12 17:59:11
【问题描述】:
我有一个 ArrayList a,它可以包含任何类型的对象。然后我需要遍历 ArrayList 的元素。如果元素实现了 Cloneable,我需要克隆该元素(意思是复制它并在内存中给它自己的位置)并将克隆的元素添加到 ArrayList b。问题在于铸造。我需要转换为正确的对象类型,然后调用 clone()。 (因为 Object 中的 clone() 是受保护的。)
在下面的代码中,我已经设法用一堆 if 语句来做到这一点。在每个元素上,我说 if Cloneable,然后嵌套在那个 if 语句中,我有更多的 if 语句,检查正确类型的实例。当程序找到正确的类型时,它会强制转换和克隆。所有这些代码都有效,但我想要一种在没有这些 if 语句的情况下进行强制转换然后 clone() 的方法,因为可能有一些我还不知道的类。有没有办法做到这一点? (我可以使用 Class.cast() 进行投射,但在此类投射上调用 clone() 没有成功。)
我尝试序列化数组列表,实现我自己的接口(使用 clone() 方法),并调用复制构造函数。这些都不适用于每种情况。据我所知,铸造然后克隆是使其工作的唯一可靠方法。如果有一种方法可以在不指定确切类的情况下进行转换和克隆,那么这将适用于每种情况。否则,我很难过,需要另一种解决方案。 (如果有一种方法可以遍历对象中的每个字段而不考虑可访问性,那也可以。)
这是我的代码:
// Establish variables
TestClass t = new TestClass();
TestClass u = new TestClass(1);
Point p = new Point();
Point q = new Point(1, 2);
// Set up ArrayList a
ArrayList a = new ArrayList();
a.add(t);
a.add(u);
a.add(p);
a.add(q);
// Get number of elements in a
int n = a.size();
// Set up ArrayList b
ArrayList b = new ArrayList();
// Clone all Cloneable elements from a into b
for (int i = 0; i < n; i++)
if (a.get(i) instanceof Cloneable)
if (a.get(i) instanceof TestClass)
b.add(((TestClass)a.get(i)).clone());
else if (a.get(i) instanceof Point)
b.add(((Point)a.get(i)).clone());
//ISSUE: I need to be able to cast and then clone based on the class a.get(i) represents, to avoid these if statements.
// Change initial variables. They change in ArrayList a (due to referencing the same memory) but not b
t.i = 2;
u.i = 3;
p.x = 3;
p.y = 4;
q.x = 5;
q.y = 6;
System.out.println(a);
System.out.println(b);
TestClass 和 Point 是我编写的类。他们实现了 Cloneable。
感谢您提供的任何帮助。
【问题讨论】:
-
您是否正在尝试为实现您的深度克隆的 any 类解决这个问题?一般来说,以这种方式使用 instanceof 往往会产生代码异味。当新班级出现后会发生什么?您应该重新考虑整体设计问题。 javapractices.com/topic/TopicAction.do?Id=31
标签: java arraylist casting clone