我正在将Java中的一些类转换为kotlin,并且在尝试从接口继承时遇到编译错误:
平台声明冲突:以下声明具有相同的JVM签名(getContentID()Ljava / lang / String;):public open fun get-content-id():String? public open fun getContentId():String?
这是界面:
interface Media {
val contentId: String
val displayRunTime: String
val genres: List<String>
val programId: String
val runTime: String
val type: String
}
这是 class :
class Airing : Media {
override val contentId: String? = null
override val displayRunTime: String? = null
override val genres: List<String>? = null
override val programId: String? = null
override val runTime: String? = null
override val type: String? = null
override fun getContentId(): String? {
return contentId
}
我是kotlin的新手 .
3 回答
您不需要声明
override fun getContentId(): String?
,因为Media
接口的val contentId: String
已被override val contentId: String?
覆盖 .您获得的错误意味着您声明的函数在JVM字节码中与已为
contentId
属性生成的getter冲突(getter具有相同的签名) .在Kotlin中,您应该直接使用属性
contentId
,而在Java中,您可以使用生成的访问器getContentId()
和setContentId(...)
.此外,Kotlin不允许您使用可为空的
String?
覆盖非空String
属性,因为基接口的用户将期望该属性具有非空值 . 您应该使用String
替换重写的属性类型,或者在界面中将它们设置为String?
.主要问题是类型
T?
包括T
和null
. 反过来,T
是T?
的子集 . 所以你不能用它的超集类型覆盖T
属性,例如:但是,您可以使用 subset type 或 subtype 覆盖
T?
属性,例如:那你的代码应该如下 . 但是,Kotlin是一个零安全系统,即使属性是 nullable 属性,也无法在不初始化的情况下定义属性:
您应该在主构造函数中引入属性,以便让客户端代码在将来初始化它们,例如:
您还可以为属性提供一些默认值,例如:
AND
getContentId
函数将与getter
冲突,因此您应将其删除 .声明为
val
的变量类似于Javafinal
变量,是不可变的,因此您无法设置为Optional ?
您的变量声明应如下所示: