I have defined the following trait:
trait Felem[T <: Felem[T]] {
def mul(that: T): T
def square: T = this.mul(this.asInstanceOf[T])
}
I also define a class based on this trait:
class F2elem(val coef: Boolean) extends Felem[F2elem] {
override def square: F2elem = this.mul(this)
...
}
My questions are about the need of "asInstanceOf" in the definition of the "square" method in the trait. If I remove it, I get the following error:
error: type mismatch;
found : Felem.this.type (with underlying type Felem[T])
required: T
def square: T = this.mul(this)
The parameter of mult must be of type T.
When calling mul(this), the this parameter is of type Felem[T], which is not and does not conform to T. There is the additional constraint that T conforms to Felem[T]. But this is not what you want, you would need the opposite, Felem[T] to conform to T.
On the other hand, in F2elem, T is exactly F2elem, so it typechecks (completley unrelated to one being a trait and the other one a class)
Here is example to show that the definition in Felem must indeed not typecheck, and that it is possible to have implementors where Felem[T] does not conform to T.
class F3elem extends Felem[F2elem] // this is 2, not 3
This declaration is correct, F2elem which is given for T satisfies T <: Felem[T].
However, an inherited this.mul(this) in square would be invalid, mult expect a T, that is F2elem, and this is F3elem. And they are unrelated.
What you probably want is that every Felem must be like F2elem, that is that T must be the type of the actual class. You can enforce this with a self type.
trait Felem [T <: Felem[T]] { this: T => /* your code */ }
When you write that, you state that in every implementation, the type of the implementation must conform to T. Doing that, it will typecheck, and you will not be allowed to instanciate F3elem above :
error: illegal inheritance; self-type F3elem does not conform to Felem[F2elem]'s selftype F2elem class F3elem extends Felem[F2elem] {
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With