Kotlin接口中的伴随对象

mic*_*tar 15 android parcelable kotlin

我正在尝试创建一个Parcelable接口,因此我需要一个像这样的接口

interface AB : Parcelable {
    companion object {
        val CREATOR : Parcelable.Creator<AB>
    }
}
Run Code Online (Sandbox Code Playgroud)

和我的两个A和B类看起来像

data class A (...): Parcelable{
    ...
    companion object {
        val CREATOR : Parcelable.Creator<AB> = object : Parcelable.Creator<AB> {
            override fun newArray(size: Int): Array<AB?> {
                return arrayOfNulls(size)
            }

            override fun createFromParcel(parcel: Parcel): AB {
                return A(parcel)
            }

        }
    }
Run Code Online (Sandbox Code Playgroud)

我正在努力在kotlin中实现这样的接口.似乎接口类不允许CREATOR

也许我采取了错误的方法,
我有一个parcelable包含一个A或B类的列表,所以我在做

parcel.readTypedList(this.list, AB.CREATOR)
Run Code Online (Sandbox Code Playgroud)

我要求列表是A或B,这就是我使用接口的原因.

有人有任何建议或可能的解决方案吗?

Jay*_*ard 27

在Kotlin中,接口可以有一个,companion object但它不是合同的一部分,必须由实现接口的类实现.它只是一个与接口相关联的对象,它有一个单例实例.所以它是一个可以存储东西的地方,但对实现类没有任何意义.

但是,您可以拥有一个由companion object类实现的接口.也许你想要更像这样的东西:

interface Behavior {
   fun makeName(): String
}

data class MyData(val data: String) {
    companion object: Behavior {  // interface used here
        override fun makeName(): String = "Fred"
    }
}
Run Code Online (Sandbox Code Playgroud)

请注意,数据类不实现接口,但companion object确实如此.

companion object接口上的A 对于存储与接口相关的常量或辅助函数很有用,例如:

interface Redirector {
    fun redirectView(newView: String, redirectCode: Int)

    companion object {
        val REDIRECT_WITH_FOCUS = 5
        val REDIRECT_SILENT = 1
    }
}

// which then can be accessed as:
val code = Redirector.REDIRECT_WITH_FOCUS
Run Code Online (Sandbox Code Playgroud)

  • 在过去,它被允许具有通用约束,这些约束表示诸如"任何具有实现Xyz的伴随对象的类"并且在早期的Kotlin中消失,希望在将来作为另一种类型的通用约束重新出现.然后你可以一起谈论一个班级及其同伴. (3认同)

Ily*_*lya 9

按照惯例,实现Parcelable接口的类还必须具有一个非空的静态字段CREATOR,该字段被称为实现Parcelable.Creator接口的类型.

您需要使用注释注释CREATOR属性@JvmField以将其公开为包含数据类的公共静态字段.

您还可以查看https://github.com/grandstaish/paperparcel - 一个注释处理器,它自动为Kotlin和Java生成类型安全的Parcelable包装器.