Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/kotlin/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sqlite/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用KClass引用作为具体化参数从JSON反序列化_Json_Kotlin_Generics_Kotlin Js_Kotlinx.serialization - Fatal编程技术网

使用KClass引用作为具体化参数从JSON反序列化

使用KClass引用作为具体化参数从JSON反序列化,json,kotlin,generics,kotlin-js,kotlinx.serialization,Json,Kotlin,Generics,Kotlin Js,Kotlinx.serialization,我试图实现一个通用的序列化框架,使用kotlinx序列化将传出和传入的消息转换为json。我正在开发一个多平台的应用程序,所以我试图让它在KotlinJVM和KotlinJS上运行 为此,我在每条消息中添加了一个type字段,并使用一个映射将每个type字符串映射到KClass。那张地图是什么类型的?它包含KClass对象,这些对象的类扩展了Message类,因此在java中,我将我的映射指定为 Map(json) } } } @可序列化 类ClientLoginMessage :Message

我试图实现一个通用的序列化框架,使用kotlinx序列化将传出和传入的消息转换为json。我正在开发一个多平台的应用程序,所以我试图让它在KotlinJVM和KotlinJS上运行

为此,我在每条消息中添加了一个
type
字段,并使用一个映射将每个
type
字符串映射到
KClass
。那张地图是什么类型的?它包含
KClass
对象,这些对象的类扩展了Message类,因此在java中,我将我的映射指定为
Map(json)
}
}
}
@可序列化
类ClientLoginMessage
:Message(Message.getMessageTypeByClass()){}

创建序列化程序的映射,如类型:

val序列化程序:Map=mapOf(
ClientLoginMessage::类到ClientLoginMessage.serializer(),
Message::类到Message.serializer()的转换
)
按如下方式传入所需的序列化程序以
Json.decodeFromString

fun fromJson(json:String):消息?{
val plainMessage=Json.decodeFromString(Json)//从Json获取类型字符串
return messageTypes.entries.find{it.value==plainMessage.type}?let{
//如何使用it.key中的KClass作为具体化参数?
decodeFromString(serializers.get(plainMessage.type)!!,Json)
}
}

您可能还想看看Kotlin内置的多态类处理:

我最终只是按照您的建议使用了内置的多态性,从那时我阅读文档时就完全忘记了这一点。谢谢你仍然回答了我最初的问题,关于如何在任意类中做到这一点。
@Serializable
open class Message(val type: String) {

    companion object {
        val messageTypes: Map<KClass<out Message>, String> = mapOf(
            ClientLoginMessage::class to "clientLoginMessage",
            Message::class to "message"
        )

        inline fun <reified T> getMessageTypeByClass(): String = messageTypes[T::class]!! // utility for defining the type in the constructors of the individual messages
    }

    fun toJson() = Json.encodeToString(this)

    fun fromJson(json: String): Message? {
        val plainMessage = Json.decodeFromString<Message>(json) // get type string from json
        return messageTypes.entries.find { it.value == plainMessage.type }?.let {
            // how can I use the KClass from it.key as reified parameter?
            Json.decodeFromString<?????>(json) 
        }
    }
}

@Serializable
class ClientLoginMessage
         : Message(Message.getMessageTypeByClass<ClientLoginMessage>()) {}