有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java成员类(内部类)如何访问外部类的实例变量?

我写了下面的代码,这些代码运行良好,但我对合成方法有一个疑问。因为这些都是为了访问私有数据而生成的。但是我有一个在成员类中使用的外部类的公共实例变量,所以为了访问实例变量,它创建了合成方法(就像在类文件中一样!!)

代码片段如下:

public class TestInnerClass {
    public int x = 10;
        public static void main(String[] args) {
            TestInnerClass test= new TestInnerClass();
            A obj = test.new A();
            obj.display();
        }

        class A {
            void display() {
            System.out.println(x);
        }
    }
}

类文件生成如下。 对于内部A类测试类$A:

import java.io.PrintStream;

class TestInnerClass$A {
    TestInnerClass$A(TestInnerClass paramTestInnerClass) {
    }

    void display() {
        System.out.println(this.this$0.x);
    }
}

为TestInReclass生成类文件:

import java.io.PrintStream;
public class TestInnerClass {
    public int x = 10;
    public static void main(String[] args) { 
        TestInnerClass test = new TestInnerClass();
        TestInnerClass tmp13_12 = test; tmp13_12.getClass(); A obj = new A();
        obj.display();
   } 

   class A {
       A() {
       }
       void display() {
           System.out.println(TestInnerClass.this.x);
       }
   }
}

因此,我的疑问是:

(一)。为什么显示方法在类文件中有不同的定义

(二)。为什么TestInnerClass类中的文件实例变量被访问为TestInnerClass。这x。但是TestInnerClass$A的类文件中的相同代码与此不同。这是0美元。x

3)为什么JVM将合成方法创建为这个$0,而实例变量是公共的


共 (2) 个答案

  1. # 1 楼答案

    您可以从外部类访问变量,因为它们位于内部类的闭包中Closures在Java中存在,但在Java字节码中不存在该概念。您看到的合成变量和访问器是使闭包在java字节码中工作所需的混乱的一部分

    完全公开:Java中的闭包实际上不是闭包。实际闭包捕获创建函数的整个环境。在Java中,内部类始终可以访问创建它的方法的外部类成员和最终局部变量。然而,它不能像在JavaScript这样的语言中那样访问非最终局部变量

  2. # 2 楼答案

    我不完全确定我是否理解您的问题,但我将尝试回答他们:

    1. why the display method is having different definition in class files?

    您不能将java文件与类似的类文件进行比较。某些特征只存在于一个世界中。内部类就是这样一个特性。它们没有直接翻译成字节码。一些代码按摩是必要的,这就是您在这里发现的

    1. why in TestInnerClass class file instance variable is accessed as TestInnerClass.this.x. but the same code is different in class file of TestInnerClass$A as this.this$0.x??

    因为在编译内部类时,对外部类(TestInnerClass.this)的隐式引用会转换为显式引用。由于此引用不能具有标识符this,因此称为this$0

    1. why JVM created synthetic method as this$0, however instance variable is public??

    这不是一种方法,据我所知,它不是公开的。它是一个存储对封闭类的对象的引用的字段。需要它才能访问该对象的x