微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

java – 为什么匿名类即使不需要也会捕获“this”?

鉴于此代码
class Foo {}

public class Test {
        public Foo makeFoo(String p,String q) {
                return new Foo(){
                        public void doSomething() {
                                System.out.println(p);
                        }
                };
        }
}

当你编译并运行javap -c -p’Test $1.class’时,你得到这个:

Compiled from "Test.java"
class Test$1 extends Foo {
  final java.lang.String val$p;

  final Test this$0;

  Test$1(Test,java.lang.String);
    Code:
       0: aload_0
       1: aload_1
       2: putfield      #1                  // Field this$0:LTest;
       5: aload_0
       6: aload_2
       7: putfield      #2                  // Field val$p:Ljava/lang/String;
      10: aload_0
      11: invokespecial #3                  // Method Foo."<init>":()V
      14: return

  public void doSomething();
    Code:
       0: getstatic     #4                  // Field java/lang/System.out:Ljava/io/PrintStream;
       3: aload_0
       4: getfield      #2                  // Field val$p:Ljava/lang/String;
       7: invokevirtual #5                  // Method java/io/PrintStream.println:(Ljava/lang/String;)V
      10: return
}

当创建匿名类时,变量p被捕获到val $p中(如预期的那样,因为它是必需的),而变量q不是(正如预期的那样,因为它不需要).但是,Test.this被捕获到这个$0,即使它不需要.这是Java规范的强制要求,还是它恰好的工作方式?为什么这样工作?

解决方法

因为它是一个内在的类,因为

An instance i of a direct inner class C of a class or interface O is associated with an instance of O,kNown as the immediately enclosing instance of i. The immediately enclosing instance of an object,if any,is determined when the object is created (§15.9.2).

JLS 8.1.3.

“即使他们不需要”,也不例外.

原文地址:https://www.jb51.cc/java/121152.html

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐