I have a scenario that is causing a type mismatch that I cannot seem to resolve. Here’s a simplified version of the code:
abstract class Msg
trait Channel[M <: Msg] {
def receive(): M
def ack(envelope: M)
}
object ChannelSender {
private var channel : Channel[_ <: Msg] = _
def assignChannel(channel : Channel[_ <: Msg]) = this.channel = channel
def test() {
val msg = channel.receive()
channel.ack(msg) // Type mismatch here
}
}
The error from the compiler is:
type mismatch; found : msg.type (with underlying type
com.msgtest.Envelope) required: _$1 where type _$1 <:
com.msgtest.Envelope
What sort of changes could I make to get this working? Additionally, the changes require that the following concrete implementation compile:
class SomeMsg extends Msg
object SomeChannel extends Channel[SomeMsg] {
def receive(): SomeMsg = { null.asInstanceOf[SomeMsg] }
def ack(envelope: SomeMsg) {}
}
object Setup {
ChannelSender.assignChannel(SomeChannel)
}
I could get it to compile under Scala 2.9 with two changes,
The first change is to use an immutable value
val c = channel, so that the path dependent typec.M2always means the same thing. The second change is to introduce a type membertype M2 = Min traitChannel. I’m not totally sure why this is necessary (could it be a bug?). One thing to note is thatc.M2is a valid type, whereasc.Mis undefined.