kotlin - 扩展功能对于分派(dispatch)接收者来说是虚拟的?

标签 kotlin

在 Kotlin 中 Declaraing extensions as members“此类函数的调度对于调度接收器类型而言是虚拟,但对于扩展接收器类型而言是静态是什么意思。”

这是否意味着“扩展函数不遵循其接收者的类类型。它遵循参数类型(?在此代码调用方法参数中)。”

请多多指教

open class Base { }

class Derived : Base() { }

open class BaseCaller {
    open fun Base.printFunctionInfo() {
        println("Base extension function in BaseCaller")
    }

    open fun Derived.printFunctionInfo() {
        println("Derived extension function in BaseCaller")
    }

    fun call(b: Base) {
        b.printFunctionInfo()   // call the extension function
    }
}

class DerivedCaller: BaseCaller() {
    override fun Base.printFunctionInfo() {
        println("Base extension function in DerivedCaller")
    }

    override fun Derived.printFunctionInfo() {
        println("Derived extension function in DerivedCaller")
    }
}

fun main() {
    BaseCaller().call(Base())   // "Base extension function in BaseCaller"
    DerivedCaller().call(Base())  // "Base extension function in DerivedCaller" - dispatch receiver is resolved virtually
    DerivedCaller().call(Derived())  // "Base extension function in DerivedCaller" - extension receiver is resolved statically
}

最佳答案

既然你已经链接了文档,我认为你已经阅读了以下部分

The instance of the class in which the extension is declared is called dispatch receiver, and the instance of the receiver type of the extension method is called extension receiver.

理解了上面的术语之后,你还需要理解以下几点

  • 如果您不了解虚拟方法,请阅读 this
  • Extensions are resolved statically .考虑以下代码块

    fun call(b: Base) {
         // This will always call extension function defined on the Base class
         // even if you pass an object of Derived class
         b.printFunctionInfo()   // call the extension function
    }
    
    // This calls the printFunctionInfo defined on the Base, even though we pass Derived
    DerivedCaller().call(Derived()) 
    

现在回答你的问题

the dispatch of such functions is virtual with regard to the dispatch receiver type, but static with regard to the extension receiver type.

有了扩展被静态解析这一点,我们已经确定无论您传递哪个对象(Base 或 Derived),call 函数总是调用在 Base 类型上定义的扩展函数。

但是会调用哪个扩展函数?一个在基类中还是在派生类中?

这取决于调用 call 函数的对象类型,如果您使用 Base 对象调用调用,那么将调用基类中的扩展,如果您使用 Derived 对象然后将调用派生类中的扩展。

关于kotlin - 扩展功能对于分派(dispatch)接收者来说是虚拟的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60473476/

相关文章:

java - 来自 Kotlin 包的 RuntimeException 的用例

android - 如何在kotlin中对包含数字的字符串进行排序

java - 依次使用不同的请求正文发出多个 API 请求

kotlin - 如果带注释的成员没有被特定 block 包围,则发出 IDE 警告

android - 如何在 Android 项目中使用谷歌翻译 api v3 将 googleapis/java-translate 库转换为自定义 api 休息请求

random - IntRange.random()如何在Kotlin中引入熵

gradle - 如何将Gradle插件发布到Artifactory?

kotlin - 阅读行并在末尾添加一些内容

android - 添加注解处理器时,Android Studio会引发重复的类错误

Android:检测打开的键盘,onApplyWindowListener 不起作用