[英]kotlin, how to use Gson to parse a generic type is a function defined with generic type
如果类类型是通用类型“ T”,如何使用Gson进行解析?
具有一个具有通用类型的类,并且在其函数中将在运行时将json字符串解析为该通用类型'T'所代表的内容。 但是得到了
java.lang.ClassCastException: com.google.gson.internal.LinkedTreeMap cannot be cast to com.example.model.content
这对于通用的'T'不起作用:
val dataType = object : TypeToken<T>() {}.type
val data = Gson().fromJson<T>(jsonStr, dataType)
这是使用“固体”类类型调用该调用的方式,其中“ Content
为Handler<Content>
传入的位置,在该处应使用通用的“ T”( IHandler<T>
)
FetchRemoteDataCommand("https", “testcontent.com", "v2/content”,
params,
Handler<Content>).execute()
这是类采用通用类型的类型: IHandler<T>
,在运行时期望'T'应该是'solid'类型,即调用时它应该是Content
类型
class FetchRemoteDataCommand<T>(scheme: String, authority: String, path: String,
params: HashMap<String, String>,
dataReadyCb: IHandler<T>) {
val mBaseUrl = "$scheme://$authority/"
val mPath = path
val mParams = params
var mDataReadyListener = dataReadyCb
override fun dispose() {……}
override fun execute() {
getRemoteData(object : Observer<ResponseBody> {
override fun onNext(responseBody: ResponseBody) {
val dataType = object : TypeToken<T>() {}.type
val jsonStr = responseBody.string()
val data = Gson().fromJson<T>(jsonStr, dataType) ***//<=== throws***
///
mDataReadyListener(data) //<== suppose to pass back the pared data back
……
}
…………
})
}
private fun getRemoteData(observer: Observer<ResponseBody>) : Unit {
val service: IRemoteRepositoryService = ServiceFactory.createRetrofitService(
IRemoteRepositoryService::class.java, mBaseUrl)
service.getRemoteData(mPath, mParams)
.subscribe(observer)
}
}
是从Henning那里得到的想法,(还有Lin Yu Cheng也有在运行时获取类的解决方案)在运行时获取类的通用类型,因此传入类类型而不是在运行时获取类型。
class FetchRemoteDataCommand<T>(scheme: String, authority: String, path: String,
params: HashMap<String, String>,
dataReadyCb: IHandler<T>, handlerClassType: Class<T>) {
val mBaseUrl = "$scheme://$authority/"
val mPath = path
val mParams = params
var mDataReadyListener = dataReadyCb
private val clazz: Class<T> = handlerClassType //findTypeArguments(this.javaClass) <== some time return null???
private fun findTypeArguments(t: Type) : Class<T> {
return if (t is ParameterizedType) {
val typeArgs = t.actualTypeArguments
typeArgs[0] as Class<T>
} else {
val c = t as Class<*>
findTypeArguments(c.genericSuperclass)
}
}
fun getClassType(): Class<T> {
return clazz
}
override fun execute() {
getRemoteData(object : Observer<ResponseBody> {
override fun onNext(responseBody: ResponseBody) {
//val dataType = object : TypeToken<T>() {}.type
//val jsonStr = responseBody.string()
//val data = Gson().fromJson<T>(jsonStr, dataType) ***//<=== throws***
/// test generic type with the passed in class type instead of reflecting at runtime
val responseRecieved = responseBody.string()
val data = Gson().fromJson(responseRecieved, getClassType())
///
mDataReadyListener(data) //<== suppose to pass back the pared data back
……
}
…………
})
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.