kotlin从小白到大神Day06 2020.7.19

这个反射还要再学一遍

内容

1.反射的基本使用
2.使用KClass创建对象
3.利用反射调用方法
4.利用反射调用属性
5.反射顶层方法

一.反射的基本使用

Java中的字节码文件是 .class
kotlin中的字节码文件时 .KClass

import kotlin.reflect.full.*

//反射
//在程序运行过程中动态地调用类的属性和方法
fun main() {
    //如何获取字节码文件类型
    //1.只知道这个类型
    val clz = Person::class

    //2.已经有对象了
    val xw = Person()
    val clz2 = xw.javaClass.kotlin

    //可以通过class对象获取类的详细信息
    println(clz.simpleName)//类名
    println(clz.qualifiedName)//全类名  有详细包路径,如 fanshe.Person
    //println(clz.supertypes) kotlin中所有类继承 Any

    //获取类的属性
    clz.memberProperties.forEach { println(it) }//获取自己和父类的所有属性
    clz.declaredMemberProperties.forEach { println(it) }//获取自己的属性

    clz.primaryConstructor.also { println(it) }//获取主构造函数
    clz.constructors.also { println(it) }//获取所有的构造函数
    
    clz.memberFunctions.forEach { println(it) }//获取自己和父类的所有方法(有Any里面的)
    clz.declaredMemberFunctions.forEach { println(it) }//获取自己声明的方法(没有Any里面的)
    clz.functions.forEach { println(it) }//自己和父类的所有的,和memberFunctions基本差不多
}
open class Father
class Person:Father(){
    var name: String = "小王"
    var age = 19
}

二.使用KClass创建对象

import kotlin.reflect.KClass
import kotlin.reflect.full.*


fun main() {
    //获取类的对象 KClass
    //将Any类型转化为Person类型
    //即Person.KClass -> Any -> Person
    val xw = createObj(Person::class) as Person

    println(xw.name)
}

//创建对象
fun createObj(clz: KClass<out Any>): Any{
    //1.使用默认  无参  的构造函数创建
    //return clz.createInstance()//即使用它的时候必须提供一个无参的构造函数

    //2.使用有参数的构造函数创建
    val priConstr = clz.primaryConstructor
    return priConstr!!.call("老王")
}

open class Father
class Person(var name: String = "小王"):Father(){
    var age = 19

    constructor():this("小王"){

    }
}

三.利用反射调用方法

import kotlin.reflect.KClass
import kotlin.reflect.full.*


fun main() {
    invokeFun(Person::class,"show")//my name is 小王 des:老王
}

//调用函数
fun invokeFun(clz: KClass<out Any>,funName: String){
    //一般地,我们调用函数时,都是这样: Person().show("ssss"),即先创建对象,然后通过对象调用函数

    //首先,获取默认的主构造函数
    val priCons = clz.primaryConstructor
    //创建对象
    val obj = priCons?.call("小王")

    //然后,查找你要调用的这个函数是否存在
    for(func in clz.functions){
        if(func.name == funName){
            //当调用类里面的方法时,必须将对象传递过去
            //默认第一个参数就是函数的对象
            //获取参数的个数
            func.parameters.forEach{
                //print("第${it.index},个参数")
                //print("参数类型为: ${it.type}")
            }
            func.call(obj,"老王")
            break
        }
    }
}

open class Father
class Person(var name: String = "小王"):Father(){
    var age = 19

    constructor():this("小王"){

    }

    fun show(des: String){
        println("my name is $name des:$des")
    }
}

四.利用反射调用属性

import kotlin.reflect.KClass
import kotlin.reflect.KMutableProperty1
import kotlin.reflect.full.*


fun main() {

    invokeProperty(Person::class,"age")
}

//访问属性
fun invokeProperty(clz:KClass<out Any>,propName: String){
    //平时访问属性就是 Person().name这种

    //首先,创建对象
    val primary = clz.primaryConstructor
    val obj = primary?.call("Android")

    //然后,查找age属性
    clz.memberProperties.find { it.name == propName }.also {
        //调用对象的get方法
        val value = it?.call(obj)
        //println("获取属性${propName}的值: $value")//获取属性age的值: 19

        //调用对象的set方法
        //将KProperty类型转化为KMutableProperty类型
        //如果属性的修饰符为private,则需要设置isAccessible为true
        if(it != null) {
            val mpro = it as KMutableProperty1<Any, Any>

            mpro.set(obj!!, 18)

            val result = it.call(obj)
            println(result)//输出了 18
        }
    }
}
open class Father
class Person(var name: String = "小王"):Father(){
    var age = 19

    constructor():this("小王"){

    }

    fun show(des: String){
        println("my name is $name des:$des")
    }
}

五.反射顶层方法

import kotlin.reflect.KClass
import kotlin.reflect.KMutableProperty1
import kotlin.reflect.full.*

fun test(){
    println("测试")
}
fun main() {
    val func = ::test
    func.call()//输出 测试

}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
回答: 要从小白到大牛,学习Kotlin需要掌握一些基本的知识和技能。首先,你可以使用交互式方式运行Kotlin代码,这可以通过使用REPL(Read-Eval-Print Loop)实现。REPL允许你逐行输入和执行Kotlin代码,这对于学习和测试代码非常有用。你可以使用Kotlin编译器提供的kotlin命令来启动REPL。\[3\] 另外,你还可以使用文本编辑工具编写Kotlin源文件,然后使用Kotlin编译器提供的kotlinc命令在命令提示行中编译Kotlin源程序。编译成功后,你可以使用kotlin命令或JDK提供的java命令来运行编译后的Kotlin程序。\[3\] 如果你想使用IntelliJ IDEA或Eclipse等集成开发环境来开发Kotlin项目,你可以创建一个新的Kotlin项目,并在项目中创建文件,编写代码,然后通过IDE提供的编译和运行功能来执行你的程序。这种方式更适合实际项目的开发。\[2\] 总之,要从小白到大牛,你需要不断学习和实践Kotlin编程,掌握基本的语法和概念,并熟悉常用的开发工具和技巧。通过不断的练习和项目实践,你可以逐渐提升自己的Kotlin编程能力,成为一名Kotlin大牛。 #### 引用[.reference_title] - *1* *2* *3* [《Kotlin小白到大牛》第3章:第一个Kotlin程序](https://blog.csdn.net/weixin_38072116/article/details/106554349)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^control_2,239^v3^insert_chatgpt"}} ] [.reference_item] [ .reference_list ]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值