Edit: Thanks to Derek pointing out the critical part of the error message, I was able to extract the critical part a bit more and it seems to be about Existential Types. If I do understand §3.2.10 Existential Quantification over Values in the language reference correctly, then val m: Map[x.type#S, x.type#S] forSome { val x: T }
is a shorthand for val m: Map[t#S, t#S] forSome { type t <: T with Singleton }
. Yet in the code below they do behave differently.
trait Type {
type S
}
class Concrete extends Type {
type S = Double
}
trait BaseWorks {
type T <: Type
val m: t#S forSome { type t <: T with Singleton }
}
class Works extends BaseWorks {
override type T = Concrete
override val m = 0.0
}
trait BaseError {
type T <: Type
val m: x.type#S forSome { val x: T }
}
class Error extends BaseError {
override type T = Concrete
override val m = 0.0
}
Refining BaseWorks
works, while refining BaseError
leads to the error error: overriding value m in trait BaseError of type Error.this.x.S forSome { val x: => Error.this.T }; value m has incompatible type
. Am I misinterpreting §3.2.10?
Original post: In the following piece of Scala code the compiler (2.9.0.1) produces an error saying that method f2
overrides nothing in Derived
.
abstract trait Type {
type T1
type T2
type P = (T1, T2)
}
class ConcreteType extends Type {
type T1 = Double
type T2 = Double
}
abstract class Base {
type T <: Type
type TP = T#P
def f1(v: TP): TP
def f2(v: T#P): T#P
def f3(v: T#P): T#P
}
class Derived extends Base {
override type T = ConcreteType
override def f1(v: TP): TP = v
override def f2(v: T#P): T#P = v
override def f3(v: TP): TP = v
}
On the other hand, overriding the function f3
with the exact same signature as shown in the code works. I would expect that both functions behave in the same way. Why is this not the case?