Kotlin泛型泛型未按计划保留类型

Kotlin reified generics does not keep the type as planned

我正在创建一个类似于Gson的类似于TypeToken的系统,并且偶然发现了一些我不了解的东西。

此代码的目的是只有一个TypeReference类具有一个可以容纳多个类的通用参数。该类将使用inline函数创建,因此用户无需了解Holder类。

请考虑以下代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
package testing

import java.lang.reflect.ParameterizedType
import java.lang.reflect.Type

abstract class TypeReference<T : Holder> {
    val type: Type = (javaClass.genericSuperclass as ParameterizedType).actualTypeArguments[0]

    override fun toString(): String {
        return type.typeName
    }
}

inline fun <reified T : Holder> create() = object : TypeReference< T >() {}

inline fun <reified WHAT> createSingle() = object : TypeReference<Single<WHAT>>() {}

class Foo

interface Holder

interface Single< T > : Holder

fun main(args: Array<String>) {
    println(create<Single<HashMap<Int, String>>>())
    println(create<Single<Foo>>())

    println(createSingle<HashMap<Int, String>>())
    println(createSingle<Foo>())
}

这是输出:

1
2
3
4
testing.Single<java.util.HashMap<java.lang.Integer, java.lang.String>>
testing.Single<testing.Foo>
testing.Single<WHAT>
testing.Single<WHAT>

在我看来,Single(对该通用名称表示抱歉)没有被"真正地"内联,并且生成了一些中间名称。

我也查看了文档,但没有找到有关此示例。

如何创建我最初打算做的事情?为什么会这样?

编辑。:

我想提出一个问题,但是他们已经知道了。

这里发布了一个非常相似的问题,据说是重复的。您也可以在后一个链接中投票。

供将来参考:在此使用Kotlin 1.2.50


我反编译这段代码,发现两个func之间有一些不同

1
2
3
4
5
6
7
8
9
10
private static final TypeReference create() {
  Intrinsics.needClassReification();                 <---- here
  return (TypeReference)(new TypeReference() {
  });
}

private static final TypeReference createSingle() {
  return (TypeReference)(new TypeReference() {
  });
}

并手动添加此代码,工作正常。 对此了解不多,找不到文档。

1
2
3
inline fun <reified WHAT > createSingle() = Intrinsics.needClassReification().let {
    object : TypeReference<Single<WHAT>>() {}
}

结果:

1
2
3
4
5
6
7
Single<java.util.HashMap<java.lang.Integer, java.lang.String>>

Single<Foo>

Single<java.util.HashMap<java.lang.Integer, java.lang.String>>

Single<Foo>