如何在不修改源代码前提下从MyChildClass实例获取MySuperClass实例
解决方案
你可以通过反射读取非静态内部类的隐式合成字段获取对应的外部类实例,无需修改原有类的源码。
Java 中所有非静态内部类的实例,都会自动持有一个指向绑定外部类实例的合成字段,主流JVM(HotSpot、OpenJDK、Oracle JDK等)实现中该字段的固定名称为this$0,参考实现代码如下:
import MySuperClass; import MySuperClass.MyChildClass; import java.lang.reflect.Field; public class OuterInstanceGetter { public static void main(String[] args) throws Exception { // 此处为模拟场景:你已拿到的MyChildClass实例 MySuperClass originSuper = new MySuperClass(); MyChildClass childInstance = originSuper.makeChild(); // 核心反射逻辑 Field outerField = MyChildClass.class.getDeclaredField("this$0"); outerField.setAccessible(true); MySuperClass bindedSuper = (MySuperClass) outerField.get(childInstance); // 验证结果 System.out.println(bindedSuper.superString); // 输出 hello System.out.println(bindedSuper == originSuper); // 输出 true,确认是同一个外部类实例 } }
注意事项
- 该方案仅适用于非静态内部类,静态内部类不会绑定外部类实例,也不存在
this$0字段 - 如果运行环境启用了Java模块系统(JPMS)限制,需要添加JVM参数开放反射权限:
--add-opens java.base/java.lang.reflect=ALL-UNNAMED(适配未命名模块场景)
内容的提问来源于stack exchange,提问作者user14787178
相关产品推荐
相关产品推荐

