首页 > 编程知识 正文

java内部类怎么使用外部类属性,内部类可以访问外部类的私有属性吗

时间:2023-05-06 12:34:52 阅读:11467 作者:1294

有以下代码。 我想知道用于创建内部类对象inner的外部类对象。 我该怎么办?

公共类外类{

公共类inner类{

私有字符串name=' peak it ';

}

publicstaticvoidmain (字符串[ ] args ) {

OuterClass outer=new OuterClass (;

inner class inner=outer.new inner class (;

//howtogetthesameouterobjectwhichcreatedtheinnerobjectback?

OuterClass anotherOuter=?

if (通告程序输出器==输出器) {

system.out.println (wasabletoreachouttotheouterobjectviainner! ' );

} else {

system.out.println (' no luck :-();

}

}

}

编辑:那么,你们中的一些人建议添加方法来修改内部类:

公共输出类输出器

return OuterClass.this;

}

但是,如果没有更改内部类的控制权,还有其他方法(只需确认)从内部类对象中获取相应的外部类对象吗?

内部类本身可以使用OuterClass.this。 在此表达式中,可以引用在JLS中描述为有限this的任何词汇封闭实例。

但是,我认为没有办法从内部类的代码以外获取实例。 当然,你可以随时介绍自己的财产。

公共输出类get outer

return OuterClass.this;

}

编辑:根据实验,用于存储对外部类的引用的字段似乎具有软件包级权限——。 至少在我使用的JDK中是这样。

编辑:使用的名称(EDCOX1(2)2) )在Java中实际上有效,尽管JLS阻止了使用。

the $ charactershouldbeusedonlyin

机械工程师协会,

rarely,to access pre-existing names on

遗留系统。

谢谢你广阔的白云! 但是如果我没有修改内部类的控制权(检查我的编辑。

@xldsh :据我所知,只要你不用反省,你就很幸运。 我觉得这好像是对包装的侵犯。 如果——内部类不想告诉您外部实例是什么,请尊重它,然后尝试设计不需要它的类。

这在Java 8中也有效吗?

OuterClass.this引用了外部类。

但它只存在于外环的源头中。 我不认为这就是我想要的手术室。

我可以带着反省做这项工作。 但是,不应该。

import java.lang.reflect.Field;

公共类输出器{

公共类inner {

}

publicstaticvoidmain (字符串[ ] args ) throws Exception { )。

//创建the inner instance

Inner inner=new Outer ().new Inner );

//gettheimplicitreferencefromtheinnertotheouterinstance

//makeitaccessible,as it has default visibility

field field=inner.class.getdeclaredfield (' this $0);

field.set accessible (真;

//de参考和铸造it

outerouter=(outer ) field.get ) inner;

system.out.println(outer );

}

}

当然,隐含引用的名称完全不可靠,就像我说的,你不应该:—)

这个问题的更常见答案是隐藏变量以及访问它们的方法。

在以下示例中,main ()的变量x从Oracle中隐藏了test.x。

类测试{

>static int x = 1;

public static void main(String[] args) {

InnerClass innerClassInstance = new InnerClass()

{

public void printX()

{

System.out.print("x=" + x);

System.out.println(", Test.this.x=" + Test.this.x);

}

}

innerClassInstance.printX();

}

public abstract static class InnerClass

{

int x = 0;

public InnerClass() { }

public abstract void printX();

}

}

运行此程序将打印:

x=0, Test.this.x=1

更多信息,请访问:http://docs.oracle.com/javase/specs/jls/se7/html/jls-6.html jls-6.6

/**

* Not applicable to Static Inner Class (nested class)

*/

public static Object getDeclaringTopLevelClassObject(Object object) {

if (object == null) {

return null;

}

Class cls = object.getClass();

if (cls == null) {

return object;

}

Class outerCls = cls.getEnclosingClass();

if (outerCls == null) {

// this is top-level class

return object;

}

// get outer class object

Object outerObj = null;

try {

Field[] fields = cls.getDeclaredFields();

for (Field field : fields) {

if (field != null && field.getType() == outerCls

&& field.getName() != null && field.getName().startsWith("this$")) {

field.setAccessible(true);

outerObj = field.get(object);

break;

}

}

} catch (Exception e) {

e.printStackTrace();

}

return getDeclaringTopLevelClassObject(outerObj);

}

当然,隐式引用的名称是不可靠的,因此您不应该为该作业使用反射。

public class Outer {

public Inner getInner(){

return new Inner(this,this.getClass());

}

class Inner {

public Inner(Outer outer, Class extends Outer> aClass) {

System.out.println(outer);

System.out.println(aClass.getName());

System.out.println();

}

}

public static void main(String[] args) {

new Outer().getInner();

}

}

如果您没有修改内部类的控件,那么refection可能会帮助您(但不推荐)。这个$0是内部类中的引用,它告诉外部类的哪个实例被用来创建内部类的当前实例。

我就是这样做的:

public class CherryTree {

public class Cherry {

public final CherryTree cherryTree = CherryTree.this;

// [...]

}

// [...]

}

当然,您需要能够修改内部类,并且每个获得内部类对象的人现在都可以访问外部类对象。就我而言,一切都很好。

示例如下:

// Test

public void foo() {

C c = new C();

A s;

s = ((A.B)c).get();

System.out.println(s.getR());

}

// classes

class C {}

class A {

public class B extends C{

A get() {return A.this;}

}

public String getR() {

return"This is string";

}

}

版权声明:该文观点仅代表作者本人。处理文章:请发送邮件至 三1五14八八95#扣扣.com 举报,一经查实,本站将立刻删除。