我有一个保存/加载框架,可以保存任意对象图。这包括非静态嵌套类的实例。
嵌套类require由其创建它们的父类的实例拥有,嵌套类使用合成字段知道它属于哪个实例。
作为一个简单的例子,我提出了这个课程:
public class Foo implements Savable {
private class Bar implements Savable {
public void saveState(Saver saver) {
saver.putInt(3);
}
}
private Bar myBar = new Bar();
public void saveState(Saver saver) {
saver.putSavable(myBar);
}
}
在“标准”编译器上,以下代码可以很好地接受对象(myBar
),找到它的父(Foo
的特定实例),并保留它的引用和孩子一起:
if (objectClass.isMemberClass()) {
//We are a member class, which means we are a non-static inner class, and therefore must save our parent.
Field[] fields = objectClass.getDeclaredFields();
//We loop through each of our fields to find the synthetic field created by the compiler that points to our parent.
for (Field f : fields) {
String name = f.getName();
//The synthetic field pointing to the parent is named something like "this$0". At least, with the "standard" compiler it is.
if (name.startsWith("this$")) {
f.setAccessible(true);
Savable parent = (Savable)f.get(objectClass);
saver.putSavable("_parent", parent);
break;
}
}
if (!saver.containsKey("_parent")) {
throw new RuntimeException("Could not find the owner of inner class: " + objectClass);
}
}
所以,就像我说的,这在“标准”编译器上运行得很好。然后在加载时,发生类似的事情,除了我寻找一个构造函数,它接受父类的实例并实例化它,传入父类。
但是!
它不适用于Android VM。没有合成字段,构造函数看起来都很正常,就像它们不接受父实例一样。
我在这里SOL吗?这个VM显然不喜欢我的方法。有什么我可以做的,而不需要内部类知道他们需要保存对其父类实例的引用吗?
答案 0 :(得分:0)
好的,事实证明我正在咆哮着错误的树。我概述的方法在Android上以及其他任何地方都能很好地运行。问题是我在这种情况下尝试实例化的类是 static 内部类。因此,虽然它是成员类,但它没有对其外部类的引用。我只需要在查找合成构造函数/字段之前检查if (!Modifier.isStatic(objectClass.getModifiers()))
。