【问题标题】:Class Linearization not working in scala 2.13类线性化在 scala 2.13 中不起作用
【发布时间】:2021-06-24 17:40:20
【问题描述】:

我正在尝试将 scala 2.12 升级到 scala 2.13.5

类线性化不适用于我,IntelliJ 和 Scala 编译器会引发错误,但理想情况下它应该可以工作。下面是问题。

trait A[E] {
  def getObject: E = {
    // some implementation
  }
}

abstract class B[T](e: Object) {
  def getObject: T = {
    // some implemntation
  }
}

class C[T] extends B[T](null) with A[String] {
  
  def myMethod(): Unit = {
    println(this.getObject.someMethodWhichIsNotInStringClassButAvailableInTClass)
  }
}

在上面的示例程序中,this.getObject 也来自A,我希望它来自B。看来我的理解是错误的。但是需要详细了解这个类linearization问题。

由于上述问题,我的代码无法编译,因为 String 类中没有所需的方法。

同样的代码可以用 scala 2.12 编译,但不能用 scala 2.13.5。

另一个参考 - https://stackoverflow.com/a/49832570/819866

【问题讨论】:

标签: scala inheritance multiple-inheritance


【解决方案1】:

这根本不应该编译......而且它确实不适合我(2.13.1):

       error: class C inherits conflicting members:
         def getObject: T (defined in trait B) and
         def getObject: String (defined in trait A)
         (note: this can be resolved by declaring an `override` in class C.)

你不能继承同名的不同方法。

此外,如果您的继承确实有效,线性化仍然可以从左到右工作:

    trait A { def foo: Sting }
    trait B extends A { def foo = "b" }
    trait C extends A { def foo = "c" }
    class D extends B with C

    println(new D().foo)

这会打印“c”。

【讨论】:

  • 好的。这可能会在 scala 2.13 中引入,因为同样适用于 2.12。另外,我忘了提到getObject 方法在特征中都声明为final,因为覆盖它们也不起作用。
  • 我是否应该创建一个具有不同名称的新方法,然后使用super[ClassType].getObject 作为解决方法调用正确的方法?另外,这是解决这个问题的正确方法吗?
  • 是的,我不知道 2.12 ...如果它确实在那里工作,那是一个错误。这应该行不通。
  • 正确的解决方法是不要给不同的方法同名:)
  • 它们实际上来自库,项目依赖于Apache Wicket,一个getObject来自LoadableDetachableModel<T>,另一个来自IModel<E>。他们都有相同的名字和相同的签名。我无法控制它。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2022-01-10
  • 2021-09-29
  • 1970-01-01
  • 2019-12-21
  • 2021-08-26
  • 2017-03-21
  • 1970-01-01
相关资源
最近更新 更多