gpt4 book ai didi

scala - 添加具有实现破坏向后兼容性的特征方法吗?

转载 作者:行者123 更新时间:2023-12-04 01:54:28 26 4
gpt4 key购买 nike

在将具有默认实现的方法添加到特征时,我对向后兼容性感到困惑。像:

上一版本

trait Foo

新版本
trait Foo {
def verifyConsistency: Option[String] = ??? // provide default implementation
}

Migration Manager将此添加报告为二进制不兼容。那是对的吗?

最佳答案

嗯,是的,它是正确的。

当你定义 trait Foo ,它将在后台创建一个(JVM)接口(interface)Foo和 (JVM) 类 Foo$class将所有方法实现定义为静态方法。相应的 java 代码看起来像这样(对于 Foo 的新定义):

interface Foo {
Option<String> verifyConsistency();
}

class Foo$class {
static Option<String> verifyConsistency(Foo self) {
Predef.???();
}
}

当你混合 Foo变成一个具体的类 Bar ,在 JVM 级别发生的是 Bar扩展接口(interface) Foo , 它实现了方法 verifyConsistency只需将调用转接到 Foo$class :
class Bar implements Foo {
Option<String> verifyConsistency() {
return Foo$class.verifyConsistency(this); // simple forwarding
}
}

之所以这样做,是因为JVM对象模型不支持多重继承。不能简单地将特征实现放在要扩展的类中,因为您只能在 JVM 上扩展单个类。

这种情况的好处是,每次具体类混合一个特征时,该类都会为特征的每个成员定义“ stub ”方法(这些方法只是转发到实际实现,这是一个静态方法)。

一个后果是,如果您向 trait 添加一个新方法,即使您定义了一个实现也不够:需要重新编译混合该 trait 的具体类(以便将新方法的 stub 添加到类中) .如果您不重新编译这些类,您的程序将无法运行,因为您现在将拥有一个假定为具体(非抽象)并扩展相应接口(interface)但实际上错过了新方法的实现的类。

在您的情况下,这意味着具有扩展接口(interface) Foo 的具体类但没有 verifyConsistency 的任何实现.

因此二进制不兼容。

关于scala - 添加具有实现破坏向后兼容性的特征方法吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18366817/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com