Animal#SuitableFood
является подтипом Food
implicitly[Animal#SuitableFood <:< Food]
Каждый экземпляр Horse
, присвоенный Animal
-типу val
, содержит новый тип SuitableFood
, который является подтипом Animal#SuitableFood
val santorin: Animal = new Horse
val santorin2: Animal = new Horse
implicitly[santorin.SuitableFood <:< Animal#SuitableFood]
implicitly[santorin2.SuitableFood <:< Animal#SuitableFood]
implicitly[santorin.SuitableFood =:= santorin2.SuitableFood] //-- fails
// ^^^^^^^ ^^^^^^^
// these types are different
implicitly[santorin.SuitableFood =:= Grass] // -- fails
val tornado = new Horse
val tornado2 = new Horse
implicitly[tornado.SuitableFood =:= tornado2.SuitableFood] // compiles!
// ^^^^^^^ ^^^^^^^
// Grass =:= Grass
implicitly[tornado.SuitableFood =:= Grass] // compiles
Подпись метода eat
для santorin: Animal
будет иметь следующий вид:
def eat(food: santorin.SuitableFood) // SuitableFood is path-dependent
santorin.SuitableFood
является подтипом Food
и Animal#SuitableFood
HorseFood
является подтипом Food
и Grass
, но не подтипом santorin.SuitableFood
или Animal#SuitableFood
implicitly[HorseFood <:< Food]
implicitly[HorseFood <:< Grass]
implicitly[HorseFood <:< santorin.SuitableFood]// -- fails
implicitly[HorseFood <:< Animal#SuitableFood]// -- fails
Вот почему вызывается метод eat
на HorseFood
тоже не работает.Потому что HorseFood
не является подтипом santorin.SuitableFood
.
И вот почему следующие работы:
santorin.eat((new HorseFood).asInstanceOf[santorin.SuitableFood])