Kotlin-Extension Functions(扩展函数)实现原理分析

kotlin中的扩展函数,实际上是在自己的类中添加了一个static final方法,将需要扩展的类,在使用的时候作为第一个参数传入方法中,然后使用。比如:
在ExtensionTest.kt中的顶级函数

 

fun String.hello(str: String): String{
    return "hello" + str + this.length
}

fun String.hello1(str: String): String{
    return "hello$str"
}

经过反编译之后生成字节码如下:

 

public final class ExtensionTestKt {
   @NotNull
   public static final String hello(@NotNull String $receiver, @NotNull String str) {
      Intrinsics.checkParameterIsNotNull($receiver, "$receiver");
      Intrinsics.checkParameterIsNotNull(str, "str");
      return "hello" + str + $receiver.length();
   }

   @NotNull
   public static final String hello1(@NotNull String $receiver, @NotNull String str) {
      Intrinsics.checkParameterIsNotNull($receiver, "$receiver");
      Intrinsics.checkParameterIsNotNull(str, "str");
      return "hello" + str;
   }
}

这其实就变成了在ExtensionTestKt这个类中的两个static final方法,而原先对String类型进行扩展,其实就是将调用扩展函数的调用者作为函数的第一个参数传入。
kotlin中的扩展函数,实际上就是通过给类添加public static final函数的做法来实现,这样做可以减少utils类的使用
扩展函数是静态解析的,是采用静态分派的过程来处理。这意味着调用的扩展函数是由函数调用所在的表达式的类型来决定的, 而不是由表达式运行时求值结果决定的。这意思其实就是在使用该扩展函数的时候,如果类本身和其子类都进行了同一个函数的扩展,这函数是不会有重写关系的,在使用的时候,只会根据需要使用该方法的对象的实际类型来决定是调用了哪个,就是相当于调用静态方法。而不是动态分派。比如:

 

open class Shape

class Rectangle: Shape()

fun Shape.getName() = "Shape"

fun Rectangle.getName() = "Rectangle"

fun printClassName(s: Shape) {
    println(s.getName())
}    

printClassName(Rectangle())

这里的输出结果是Shape
其实很明显,因为扩展函数就是相当于一个静态方法,而调用静态方法是没有重写,所以子类并不会影响父类。
如果一个类定义有一个成员函数与一个扩展函数,而这两个函数又有相同的接收者类型、 相同的名字,并且都适用给定的参数,这种情况总是取成员函数。

 

class Example {
    fun printFunctionType() { println("Class method") }
}

fun Example.printFunctionType() { println("Extension function") }

Example().printFunctionType()

这段代码输出“Class method”。



作者:zzq_nene
链接:https://www.jianshu.com/p/e056a59cb7f1
来源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值