Kotlin函数扩展和属性扩展

2022-11-25  本文已影响0人  因为我的心

一、前言:

我们都知道java要扩展一个已有类的方法和属性必须采用继承、组合或直接修改现有类来进行功能和属性的扩展。而kotlin是完全支持扩展方法和扩展属性的,这样我们就可以像正常调用对象方法一样使用扩展方法和属性了。

二、扩展方法

1、扩展方法的定义语法如下:

fun [扩展类].(参数列表){
    //方法执行体
}

示例:

   override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        //创建对象
        val apple = Apple()
        apple.test()
        //使用的时候和调用普通方法没有任何区别
        apple.info()
    }


    //1、Apple类
    class Apple{
        fun test(){
            Log.d("LUO","test")
        }
    }
    //2、给Apple扩展了一个info方法
    fun Apple.info(){
        Log.d("LUO","info")
    }

2、kotlin也是支持泛型类的扩展的,比如我们为List添加一个交换两个元素位置的方法代码如下:

fun MutableList<Int>.swap(index1: Int, index2: Int) {
    val tmp = this[index1] // “this”对应该列表
    this[index1] = this[index2]
    this[index2] = tmp
}
//使用
fun main(args:Array<String>) {
    val list = mutableListOf(1, 2, 3)
    list.swap(0,1)
    Log.d("LUO","list = $list")
}

3、扩展的实现机制

kotlin的扩展其实是没有修改原来的类的。kotlin扩展的本质其实就是定义了一个函数,当程序用对象调用扩展方法时,kotlin在编译时会执行静态解析(就是根据调用对象、方法名来找到扩展函数,转换为函数调用)。
kotlin在编译时会经过一下几步:

三、扩展属性

扩展属性有以下原则:

1、顶级的方法去定义扩展方法(属性)

示例代码:

 override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        var user = User("赵","薇薇")
        var name =  user.fullName
        Log.d("LUO","---name:$name")
        user.fullName = "我是.小明"
        Log.d("LUO","---name:${user.fullName}")
    }

    //1、User对象
    class User(var firstName: String, var lastName: String) {}
    
    //2、为 User的fullName 扩展读写属性
    var User.fullName: String
        get() = "${firstName}.${lastName}"
        set(value) {
            Log.d("LUO","执行扩展属性 fullName setter 方法")
            //value 字符串中不包含.或包含几个 都不行
            if ("." !in value || value.indexOf(".") != value.lastIndexOf(".")) {
                Log.d("LUO","您输入的 fullName 不合法")
            } else {
                var tokens = value.split("·")
                firstName = tokens[0]
                lastName = tokens[1]
            }
        }

2、以成员的方式扩展方法

kotlin也支持以成员的方法定义扩展和属性。
对于成员的方式定义的扩展,

示例代码如下:

class A {
    fun bar() = println("A类的bar方法")
}

class B {
    fun baz() = println("B类的baz方法")
    fun A.foo() {
        this.bar()//this指的是被扩展类。
        this@B.baz()//this可以省略
    }

    fun test(target: A) {
        target.bar()//调用目标类的成员方法
        target.foo()//调用目标类的扩展方法
    }
}
//测试程序
fun main(args: Array<String>) {
    var b = B()
    b.test(A())
}

输出结果:

A类的bar方法
A类的bar方法
B类的baz方法

注意:如果扩展类和扩展方法所在类中的方法签名一致,那么如果不加this@类名指定调用哪个类的方法时,默认调用的是被扩展类的同名方法。

四、什么情况用扩展


参考:https://blog.csdn.net/guojingbu/article/details/121196705

上一篇下一篇

猜你喜欢

热点阅读