【问题标题】:Why is this$0 field of an inner class not private?为什么内部类的这个 $0 字段不是私有的?
【发布时间】:2019-02-08 08:12:47
【问题描述】:

Java 内部类将外部实例的引用存储在合成字段中:

class A {
    class B {}
}

java.util.Arrays.toString(A.B.class.getDeclaredFields())
// [final A A$B.this$0]

我想知道为什么这个字段不是作为私有生成的。

没有反射就不能被程序员访问(在B之外,A.this指的是它)。

明显的猜测是你可以在A(B之外)写一些需要访问它的东西,但我想不出这样的情况。

【问题讨论】:

  • 你应该看到this
  • 我正要说“这样这个字段可以在创建时由外部类设置”,但这当然也适用于私有字段......
  • @Novy 你能解释一下为什么吗?我没有看到任何我不知道的东西。
  • @Alexey Romanov 在我看来,为什么是因为在 java 中默认字段、方法和类是包私有的,这意味着它们不能从包外部访问。生成 A$B.this$0 生成的类是 A$B 作为生成的字段,它尊重默认值。 A$B.this$0 是对外部 this(A.this) 的引用。因此,如果您在 A(在 B 之外),您已经可以访问 A.this。不知道是不是你要的东西
  • 我相信我找到了答案。

标签: java


【解决方案1】:

我想错了方向。需要访问B.this$0 的不是A,而是B 本身的潜在内部类!

如果我们有

class A {
    class B {
        class C {}
    }
}

那么在脱糖后C就变成了

class A$B$C {
    final A$B this$1;

    A$B$C(A$B b) {
        this$1 = b;
    }
}

和C 内的A.this 必须以this$1.this$0 访问。或者,它可以有两个字段

    final A$B this$1;
    final A this$0;

在这种情况下,构造函数将包含this$0 = b.this$0;(这实际上是我在检查之前所期望的)。

【讨论】:

    猜你喜欢
    • 2011-10-22
    • 1970-01-01
    • 1970-01-01
    • 2012-02-28
    • 2011-03-03
    • 2014-10-02
    • 2020-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多