为什么SomeClass :: class是KClass ,但是这个:: class是KClass
我想打印我的类的属性的值。
fun print() { val cl = this::class cl.declaredMemberProperties.filter {it.visibility != KVisibility.PRIVATE}.forEach { println("${it.name} = ${it.get(this)}") } }
当我尝试构建此代码时,出现编译器错误:
Error:(34, 40) Kotlin: Out-projected type 'KProperty1' prohibits the use of 'public abstract fun get(receiver: T): R defined in kotlin.reflect.KProperty1'
当我改变this
类名SomeClass
一切都很好
fun print() { val cl = SomeClass::class cl.declaredMemberProperties.filter {it.visibility != KVisibility.PRIVATE}.forEach { println("${it.name} = ${it.get(this)}") } }
所以问题是this::class
编译器KClass
器types为KClass
而不是使用KClass
。 任何想法为什么会发生?
造成这种差别的原因是,当使用SomeClass::class
引用时,肯定是表示SomeClass
的类标记,而不是其可能的派生类,因此它是KClass
没有types投影。
但是this::class
写在一个open
或abstract
类或扩展函数函数中的类可以返回一个派生类的类标记,因此,为了确保types的安全性, types是out
KClass
: KClass
意味着实际的types参数可以是SomeClass
或其子types。
例:
open class A { fun f() { println(this::class) // KClass because it can be KClass } } class B : A() B().f()