【问题标题】:Scala reflection: Why does getMethods return private vals defined in superclass?Scala 反射:为什么 getMethods 返回超类中定义的私有 val?
【发布时间】:2017-10-26 16:29:33
【问题描述】:

下面的代码定义了一个 trait T 和一个私有 val someVal 和一个扩展 T 的匿名类。如果我们从匿名类的实例中调用getMethods,someVal 被列为公共方法:

scala> trait T { private val someVal = 3 }
defined trait T

scala> new T {}.getClass.getMethods.apply(0)
res2: java.lang.reflect.Method = public int $anon$1.$line6$$read$T$$someVal()

当然someVal 在这个子类中是不可访问的,但是为什么即使在getMethods 的返回中,作为公共的呢?

【问题讨论】:

  • 反射很少是更好的解决方案

标签: scala reflection


【解决方案1】:

traits 编译为interfaces,因为它们需要多重继承。但是接口既不能有字段也不能有非public 成员。因此,一个字段变成了一对public 访问器,被特征名称修饰,编译器的任务是将该字段放入所有子类并实现访问器。 T 上尝试访问someVal 的任何方法都通过getter,而包含构造函数代码的static $init$ 函数使用setter 将其设置为3。如果您的val 被声明为public,那么getter 的名称将被分解为someVal,外部代码将使用它,如果它也是var,则setter 将分解为someVal_= ,随后被破坏为someVal_$eq。无论如何,这些可怕的长名字已经足以阻止任何人使用它们,而且它仅在进行 Java 互操作时才相关。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-10-22
    • 1970-01-01
    • 2018-04-07
    • 1970-01-01
    • 2013-10-24
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多