??通過反射調(diào)用函數(shù)需要 KFunction
實(shí)例幔戏,KFunction
實(shí)例可以通過兩種方式獲得:一種是函數(shù)引用;另外一種是通過 KClass
提供的 API 獲得 KFunction
實(shí)例披诗。
??函數(shù)引用可以表示一個(gè)函數(shù)字面量,可以賦值給函數(shù)類型變量立磁。函數(shù)引用也是使用 ::
運(yùn)算符呈队,可以引用頂層函數(shù)也可以引用類中的成員函數(shù)。
- 通過反射調(diào)用函數(shù)的示例代碼如下:
class Person() {
var name: String? = null
var age: Int = 0
fun setNameAndAge(name: String, age: Int) {
this.name = name
this.age = age
}
override fun toString(): String {
return "Person [name=$name, age=$age]"
}
}
fun add(a: Int, b: Int): Int = a + b
fun sub(a: Int, b: Int) = a - b
fun calculate(opr: Char): (Int, Int) -> Int = if (opr === '+') ::add else ::sub
fun main(args: Array<String>) {
val fn1 = ::add // 1??
val fn2 = ::sub // 2??
val fn3 = calculate('+') // 3??
println(fn1.call(10, 5)) // 4??15
println(fn1(10, 5)) // 5??15
println(fn2(10, 5)) // 5
println(fn3(10, 5)) // 15
val clz = Person::class // 6??
val person = clz.createInstance() // 7??
clz.functions.forEach { println(it.name) } // 8??
val pfn1 = clz.functions.first()
pfn1.call(person, "小三", 18)
println(person)
val pfn2 = Person::setNameAndAge
pfn2.call(person, "小五", 15)
println(person)
pfn2.call(person, "小雪", 20)
println(person)
}
運(yùn)行結(jié)果:
15
15
5
15
setNameAndAge
toString
equals
hashCode
Person [name=小三, age=18]
Person [name=小五, age=15]
Person [name=小雪, age=20]
Process finished with exit code 0
??上面代碼第1??唱歧、2??行都是引用頂層函數(shù)宪摧。代碼第3??行調(diào)用 calculate
函數(shù),該函數(shù)的返回類型是函數(shù)類型 (Int, Int) -> Int
颅崩,函數(shù)引用可以作為函數(shù)字面量表示函數(shù)几于,所以 calculate
函數(shù)直接返回函數(shù)引用。這也說明了 KFunction
類型與函數(shù)類型是兼容的沿后。
??代碼第4??行是通過 KFunction
的 call
函數(shù)調(diào)用引用的函數(shù)沿彭,也可以通過第5??行直接調(diào)用函數(shù)。
??代碼第6??行是引用 Person
類實(shí)例尖滚,代碼第7??行是通過引用類創(chuàng)建實(shí)例 Person
喉刘,createInstance
函數(shù)能夠創(chuàng)建引用類的對(duì)象。代碼第8??行 functions
是 KClass
屬性漆弄,它可以獲得當(dāng)前類中的所有函數(shù)睦裳。