【问题标题】:Kotlin: Access a public field from a Java class that also overrides a public getter of the same nameKotlin:从 Java 类访问公共字段,该类也覆盖同名的公共 getter
【发布时间】:2019-03-14 09:15:53
【问题描述】:

我有一个 Java 类(我无法编辑,因为它是由 Thrift 自动生成的)定义如下:

public class TheirException extends Throwable {
  public String message;

  public TheirException(String message) {
    this.message = message;
  }

  public String getMessage() {
    return this.message;
  }
}

但是,如果我尝试从 Kotlin 获取 message,getMessage() 不可用并产生 Unresolved reference 错误。尝试使用 messagefield 会产生以下错误:

错误:(470, 30) Kotlin:重载分辨率歧义:
公共最终变量消息:字符串!在 com.example.TheirException
中定义 public open val 消息:字符串?在 com.example.TheirException 中定义

但是,如果我这样做:

(exception as Throwable).message

解决得很好。

为什么这里需要强制转换为Throwable,为什么getMessage() 不可用,是什么导致了歧义?

【问题讨论】:

  • 你可以试试getFoo()吗? kotlin 也允许使用相同的方法名进行访问。
  • 你使用的是什么 kotlin 版本?在 1.3 中,javaClass.foo 指向字段,javaClass.getFoo() 指向方法
  • 为什么你有一个带有公共 getter 的公共字段?将字段设为私有!
  • @Deepak getFoo() 不可用“未解决的参考”。 @Lino 版本 1.3.20 @Seelenvirtuose 问题是关于如何使用从 Kotlin 生成的类,而不是关于如何更改原始类。
  • 在 kotlin 1.3 中,我能够使用 .foo 和 .getFoo() 编译和执行代码

标签: java kotlin


【解决方案1】:

歧义是由于message 是公开的这一事实造成的。 Kotlin 将每个 getter 转换为一个属性即使没有支持字段。如果你在这个类中添加另一个函数:

public String getSecondMessage() {
  return "second message"; // Note that this getter does not rely on a field
}

你可以在 Kotlin 中这样访问它:

TheirException("message").secondMessage

如果message 是公开的,并且有一个getMessage() 函数,Kotlin 会创建 2 个 getter,并且在调用站点上你新人知道该使用哪个。在您的示例中,2 个吸气剂将具有相同的行为,但情况并非总是如此。

当您将您的类转换为Throwable 时,您明确告诉编译器该类具有Throwable 的签名,这意味着您定义应该只有一个message getter,这解决了歧义。请注意,Kotlin 有自己的 Throwable 定义(稍后会很重要)。

现在你可能会问为什么没有getMessage() 函数。这是因为您正在投射到 Throwable 而不是 java.lang.Throwable。 Throwable 的 Kotlin 定义没有 getMessage()

【讨论】:

  • 感谢您的回答。虽然这解释了歧义,但是否有一种访问原始方法的 kotlin 方式?我能想到的一件事是创建一个明确的 java 访问器
  • 创建显式 java 访问器可以解决问题,另一种解决方案是使用反射显式调用方法。
  • 如果我创建一个类并添加一个公共字段和一个 getter,它们都可以从 Kotlin 访问。只是添加了导致问题的继承,所以我认为您的解释不正确。
猜你喜欢
  • 2020-06-20
  • 2021-09-14
  • 2013-09-11
  • 2010-12-30
  • 2023-03-28
  • 2019-06-24
  • 1970-01-01
  • 1970-01-01
  • 2014-01-26
相关资源
最近更新 更多