dependencies {
// kotlin反射库,大小2.5M左右
implementation “org.jetbrains.kotlin:kotlin-reflect:1.4.20”
}
没错,有2.5M,不过编译后的大小还能接受
kotlin获取KClass通过两个冒号
var cls: KClass = String::class
cls.java // 转成java的Class
cls.java.kotlin // 再转回到kotlin的KClass
// 获取定义在类中的属性(直接写在类当中的)
val property = cls.declaredMemberProperties.firstOrNull()
KClass是不带泛型的类,typeOf能拿到具体的泛型实际类型:
val mapCls = Map::class
println(mapCls) // 输出class kotlin.collections.Map
val mapType = typeOf<Map<String, Int>>() // 拿到 KType
mapType.arguments.forEach { // 拿到 KType 中的每个参数泛型的类型
println(it) // 输出 kotlin.String 和 kotlin.Int
}
拿到KClass之后可以通过KClass的方法获取各种其他属性了
一个简单的示例:
open class S(val sex : Boolean) {
fun superFun() {
}
}
class A(val name : String, sex: Boolean) : S(sex) {
fun String.hello(){
}
fun foo() {
}
var age : Int = 0;
}
fun A.test() {
}
上面的class A继承了一个类,并且类的内部有其他类定义的扩展方法,本身也定义了一个扩展方法。
KClass提供了很多方法获取类的属性和方法,但是有一些区别,方法比较多,可以看一下区别:
fun main() {
// 能得到:age, name, foo(), (String.)hello(), equals(), hashCode(), toString(), sex, superFun()
println(A::class.members) 获取所有的成员属性和方法,包括其他类的扩展方法,包括父类的方法,但不包括构造方法
// 能得到:foo(), (String.)hello(), equals(), hashCode(), toString(), superFun()
println(A::class.functions) 获取所有的方法, 包括扩展方法,包括父类的
// 能得到:age, name, sex
println(A::class.memberProperties) 获取所有的成员属性 非扩展, 包括父类
// 能得到:foo(), equals(), hashCode(), toString(), superFun()
println(A::class.memberFunctions) 获取所有的成员方法 非扩展