Si è imbattuto in questo strano comportamento quando si è modificato il limite superiore dell'implementazione, ma si è dimenticato di modificarlo nell'interfaccia. Penso che l'ultima affermazione non dovrebbe essere compilata, ma lo fa e restituisce risultati inaspettati.Strano comportamento di inferenza di tipo in funzione con limite superiore
trait SuperBase
trait Base extends SuperBase
class SuperBaseImpl extends SuperBase
trait Service {
def doWork[T <: Base : Manifest](body: T => Unit): String
def print[T <: Base : Manifest]: String
}
object ServiceImpl extends Service {
override def doWork[T <: SuperBase : Manifest](body: T => Unit): String =
print[T]
def print[T <: SuperBase : Manifest]: String =
manifest[T].runtimeClass.toString
}
val s: Service = ServiceImpl
// does not compile as expected
// s.print[SuperBaseImpl]
// returns "interface Base"
s.doWork { x: SuperBaseImpl =>() }
Modifica
Come @ som-snytt menzionato con -Xprint:typer
opzione possiamo vedere ciò che realmente compilatore inferisce:
s.doWork[Base with SuperBaseImpl]
Questo spiega il motivo per cui stiamo ottenendo "interfaccia di base". Ma ancora non capisco come e perché digitare il lavoro di inferenza in questo caso.
Grazie, ma penso che sia più semplice definire semplicemente 'T' esplicitamente:' s.doWork [SuperBaseImpl] {x =>()} '. –