Java:Class.this

Joh*_*azz 106 java class this

我有一个看起来像这样的Java程序.

public class LocalScreen {

   public void onMake() {
       aFuncCall(LocalScreen.this, oneString, twoString);
   }
}
Run Code Online (Sandbox Code Playgroud)

LocalScreen.this意味着什么aFuncCall

aio*_*obe 159

LocalScreen.thisthis封闭类.

这个例子应该解释一下:

public class LocalScreen {

    public void method() {

        new Runnable() {
            public void run() {
                // Prints "An anonymous Runnable"
                System.out.println(this.toString());

                // Prints "A LocalScreen object"
                System.out.println(LocalScreen.this.toString());

                // Won't compile! 'this' is a Runnable!
                //onMake(this);

                // Compiles! Refers to enclosing object
                onMake(LocalScreen.this);
            }

            public String toString() {
                return "An anonymous Runnable!";
            }
        }.run();
    }

    public String toString() { return "A LocalScreen object";  }

    public void onMake(LocalScreen ls) { /* ... */ }

    public static void main(String[] args) {
        new LocalScreen().method();
    }
}
Run Code Online (Sandbox Code Playgroud)

输出:

An anonymous Runnable!
A LocalScreen object
Run Code Online (Sandbox Code Playgroud)

该帖子已被改写为一篇文章在这里.


SLa*_*aks 54

它表示this外部LocalScreen类的实例.

this没有限定符的写入将返回调用所在的内部类的实例.

  • 还是不太明白.当我将其编码为"LocalScreen.this"与"this"相比时有什么区别?我测试了两者,编译器只接受"LocalScreen.this".aFuncCall的第一个参数是aParent类,它是父类"Somethig". (4认同)
  • @rascher:正在使用内部类; OP没有将它们包含在代码段中.仅在非静态内部类中支持此语法. (4认同)

Tof*_*eer 14

编译器接受代码并使用它执行类似的操作:

public class LocalScreen 
{
    public void method() 
    {
        new LocalScreen$1(this).run;
    }

    public String toString() 
    {
        return "A LocalScreen object"; 
    }

    public void onMake(LocalScreen ls) { /* ... */ }

    public static void main(String[] args) 
    {
        new LocalScreen().method();
    }
}

class LocalScreen$1
     extends Runnable
{
    final LocalScreen $this;

    LocalScreen$1(LocalScreen $this)
    {
        this.$this = $this;
    }

    public void run() 
    {
        // Prints "An anonymous Runnable"
        System.out.println(this.toString());

        // Prints "A LocalScreen object"
        System.out.println($this.toString());

        // Won't compile! 'this' is a Runnable!
        //onMake(this);

        // Compiles! Refers to enclosing object
        $this.onMake($this);
    }

    public String toString() 
    {
        return "An anonymous Runnable!";
    }
}
Run Code Online (Sandbox Code Playgroud)

正如您所看到的,当编译器使用内部类时,它会将其转换为外部类(这是一个很久以前的设计决策,因此不需要更改VM来理解内部类).

当创建非静态内部类时,它需要对父类的引用,以便它可以调用外部类的方法/访问变量.

内部类的内部不是正确的类型,您需要访问外部类以获得调用onMake方法的正确类型.


Naw*_*Man 12

Class.this允许访问外部类的实例.请参阅以下示例.

public class A
{
  final String name;
  final B      b;
  A(String name) {
    this.name = name;
    this.b = new B(name + "-b");
  }

  class B
  {
    final String name;
    final C      c;
    B(String name) {
      this.name = name;
      this.c = new C(name + "-c");
    }

    class C
    {
      final String name;
      final D      d;
      C(String name) {
        this.name = name;
        this.d = new D(name + "-d");
      }

      class D
      {
        final String name;
        D(String name) {
          this.name = name;
        }

        void printMe()
        {
          System.out.println("D: " + D.this.name); // `this` of class D
          System.out.println("C: " + C.this.name); // `this` of class C
          System.out.println("B: " + B.this.name); // `this` of class B
          System.out.println("A: " + A.this.name); // `this` of class A
        }
      }
    }
  }
  static public void main(String ... args)
  {
    final A a = new A("a");
    a.b.c.d.printMe();
  }
}
Run Code Online (Sandbox Code Playgroud)

然后你会得到.

D: a-b-c-d
C: a-b-c
B: a-b
A: a
Run Code Online (Sandbox Code Playgroud)