首页 > 解决方案 > Kotlin - 在运行时确定嵌套的泛型类型

问题描述

我的解决方案中有以下课程

open class State<T : Any> { ... }

class CustomState : State<BigDecimal> { ... }

abstract class FindState<T : State<*>> { ... }

class FindStateImpl<T : State<*>> : FindState<T>() { ... }

FindState可以这样称呼

val strState = FindStateImpl<State<String>>(...)

val intState = FindStateImpl<State<Int>>(...)

val customState = FindStateImpl<CustomState>(...)

FindState我需要能够在运行时获得的类内部,类类型为:

因此,对于上面的示例,我需要获得:

val strState = FindStateImpl<State<String>>(...)
//State::class.java
//String::class.java

val intState = FindStateImpl<State<Int>>(...)
//State::class.java
//Int::class.java

val customState = FindStateImpl<CustomState>(...)
//CustomState::class.java
//BigDecimal::class.java (since string is the underlying type T)

到目前为止,我有这样的东西,但它很可怕并且不能完全工作:

val stateType = javaClass.kotlin.supertypes[0].arguments[0].type?.jvmErasure?.javaObjectType

是否可以在运行时获取这些类型?

标签: kotlin

解决方案


您提供的代码根本不包含所需的类型信息,因为它将被删除。只有将特定类型指定为超类型一部分的子类型才可用。

使用 kotlin 有两种方法可以检索类型信息:

  1. 使用像 Guava 这样的模式TypeToken,并确保提供一个包含所需类型信息的匿名对象。这将使反射代码工作。
  2. 在编译期间使用一个具体化的方法和typeOf<T>()嵌入的方法:KType
inline fun <reified T : Any, CS : State<T>> FindStateEmbedType(state: CS): FindState<CS> {
    val contentType = typeOf<T>();
    // Do what you need to do with T, perhaps embed in a wrapper FindState type
    return FindStateImplWithType(state, contentType)
}

推荐阅读