简体   繁体   English

覆盖Scala中通用特征的方法

[英]Overriding the method of a generic trait in Scala

I defined a generic Environment trait: 我定义了一个通用的环境特征:

trait Environment[T]

For which I provide this implementation: 为此我提供了这个实现:

class MyEnvironment extends Environment[Integer] {
 val specific: Integer = 0
}

Furthermore, I defined a generic Event trait that has one method that accepts a generic Environment as parameter: 此外,我定义了一个通用事件特征,它有一个接受通用环境作为参数的方法:

trait Event[T] {
  def exec(e: Environment[T])
}

For this Event trait, I provided the following implementation, where the exec() method accepts a parameter of the type MyEnvironment, to enable me to access the specific value of MyEnvironment. 对于此事件特征,我提供了以下实现,其中exec()方法接受MyEnvironment类型的参数,以使我能够访问MyEnvironment的特定值。

class MyEvent extends Event[Integer] {
  override def exec(e: MyEnvironment): Unit = {
    println(e.specific)
  }
}

However, the Scala compilers outputs an error, from where it seems that MyEnvironment is not recognized as an Environment[Integer]: 但是,Scala编译器输出一个错误,似乎MyEnvironment似乎不被识别为Environment [Integer]:

Error: method exec overrides nothing. 错误:方法exec不会覆盖任何内容。

Note: the super classes of class MyEvent contain the following, non final members named exec: def exec(t: main.vub.lidibm.test.Environment[Integer]): Unit 注意:类MyEvent的超类包含以下非最终成员,名为exec:def exec(t:main.vub.lidibm.test.Environment [Integer]):Unit

Is it possible to make this work, or are there patterns to circumvent this problem. 是否有可能使这项工作,或有模式来规避这个问题。

You can't narrow down the signature of a method; 你不能缩小方法的签名; it's not the same method any more. 它不再是同一种方法了。 In your case, you can't override 在您的情况下,您无法覆盖

def exec(e: Environment[T]): Unit

with

override def exec(e: MyEnvironment): Unit 

Second method is more specific than the first one. 第二种方法比第一种方法更具体。 It's conceptually the same as eg overriding def foo(a: Any) with def foo(s: String) . 它在概念上与使用def foo(s: String)重写def foo(a: Any)相同。

If you want it to work, you need to use the same type in both signatures (note that if you use an upper bound such as T <: Environment[_] , that means that a method that accepts T actually accepts any subclass of Environment , so overriding using MyEnvironment will work OK in that case). 如果你想要它工作,你需要在两个签名中使用相同的类型(请注意,如果你使用上限,如T <: Environment[_] ,这意味着接受T的方法实际上接受Environment任何子类,所以在这种情况下使用MyEnvironment覆盖将正常工作)。

Because overriding is not polymorphic in the method's parameter types. 因为覆盖在方法的参数类型中不是多态的。 It works the same way as in Java. 它的工作方式与Java相同。 In the example what you have done is overloaded the method in reality.That is they are treated as different methods. 在示例中,您所做的是在实际中重载该方法。这就是它们被视为不同的方法。
For overriding the method names ie. 用于覆盖方法名称,即。 the name , signature , types has to be the same. 名称,签名,类型必须相同。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM