【发布时间】:2017-11-23 17:28:06
【问题描述】:
我是 Kotlin 的新手。 当我学习Storing Properties in a Map。我尝试以下用法。
class User(val map: MutableMap<String, String>) {
val name: String by map
}
class User(val map: MutableMap<String, in String>) {
val name: String by map
}
class User(val map: MutableMap<String, out String>) {
val name: String by map
}
前两个都可以,最后一个失败。
加上out修饰符,getName的字节码是这样的:
public final java.lang.String getName();
0 aload_0 [this]
1 getfield kotl.User.name$delegate : java.util.Map [11]
4 astore_1
5 aload_0 [this]
6 astore_2
7 getstatic kotl.User.$$delegatedProperties : kotlin.reflect.KProperty[] [15]
10 iconst_0
11 aaload
12 astore_3
13 aload_1
14 aload_3
15 invokeinterface kotlin.reflect.KProperty.getName() : java.lang.String [19] [nargs: 1]
20 invokestatic kotlin.collections.MapsKt.getOrImplicitDefaultNullable(java.util.Map, java.lang.Object) : java.lang.Object [25]
23 checkcast java.lang.Object [4]
26 aconst_null
27 athrow
Local variable table:
[pc: 0, pc: 28] local: this index: 0 type: kotl.User
正如我们所见,它会导致NullPointerException。
为什么地图委托上不允许逆变?
为什么 kotlin 没有给我编译错误?
【问题讨论】:
-
你不应该在那里使用逆变,因为地图 产生 值。您没有收到编译器警告的事实可能是一个错误。实际上
out是协变的,in是逆变的。出于某些的原因,使用in会产生我期望使用out的代码。
标签: delegates jvm kotlin generic-variance