Android Parcelable 问题 - 解组时出现 ClassNotFoundException

问题描述

我有一个对象列表如下:

data class MyProduct(
    var id: String?,var name: String?
) : Parcelable {

    override fun writetoParcel(parcel: Parcel,flags: Int) {
        parcel.writeString(id)
        parcel.writeString(name)
    }

    override fun describeContents(): Int {
        return 0
    }

    companion object CREATOR : Parcelable.Creator<MyProduct> {
        override fun createFromParcel(parcel: Parcel) = MyProduct(
            id = parcel.readString(),name = parcel.readString(),)

        override fun newArray(size: Int): Array<MyProduct?> = arrayOfNulls(size)
    }
}

MutableList<MyProduct>

我需要使用事件广播器来分享这个。我有一个方法如下:

    fun sendMyProduct(myProducts: MutableList<MyProduct>) {
        intentbroadcaster.broadcastMessage(
            event = EVENT_MY_PRODUCTS,data = MyProductsUpdated(
                myProducts = myProducts
            )
        )
    }

MyProductsUpdated一个可分割的类。

data class MyProductsUpdated(
    val myProducts: MutableList<MyProduct>
) : Event {

    override fun writetoParcel(parcel: Parcel,flags: Int) {
        parcel.writeList(myProducts)
    }

    override fun describeContents(): Int {
        return 0
    }

    companion object CREATOR : Parcelable.Creator<MyProductsUpdated> {
        override fun createFromParcel(parcel: Parcel) = MyProductsUpdated(
            myProducts = parcel.readParcelable(MyProduct::class.java.classLoader)!!
        )

        override fun newArray(size: Int): Array<MyProductsUpdated?> = arrayOfNulls(size)
    }
}

当我需要在广播后检索数据时,我会执行以下操作:

    private fun myProductsUpdated(action: String,extras: Bundle) = invokeCallbacks(action) {
        extras.getParcelable<MyProductsUpdated>(Events.DATA)!!
    }

我并不完全相信我将列表作为可包裹读取或写入的处理是正确的。

当我尝试使用它时,我遇到了以下崩溃:

java.lang.RuntimeException: Error receiving broadcast Intent

即:

Caused by: android.os.BadParcelableException: ClassNotFoundException when unmarshalling: ��9
        at android.os.Parcel.readParcelableCreator(Parcel.java:2556)
        at android.os.Parcel.readParcelable(Parcel.java:2482)
        at com.xx.services.MyProductUpdated$CREATOR.createFromParcel(MyProductsUpdated.kt:26)
        at com.xx.services.events.MyProductsUpdated$CREATOR.createFromParcel(MyProductsUpdated.kt:24)

我相信这个问题与我正在写一个“列表”但只是阅读一个parcelable有关,但我不太确定如何解决这个问题。任何帮助将不胜感激。

解决方法

您应该使用 readList,而不是 readParcelable。将内容读入现有列表。

myProducts = mutableListOf<MyProduct>().apply {
    parcel.readList(this,MyProduct::class.java.classLoader)
}

还可以考虑使用 the Parcelize plugin 来节省一些时间。

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...