Как определить, расширяет ли тип Scala определенный родительский класс? - PullRequest
1 голос
/ 16 января 2012

В Scala я извлекаю тип данного класса через манифест Scala и сохраняю его.Мой вопрос заключается в следующем: как я могу проверить этот тип, чтобы увидеть, произошел ли исходный класс от одного родительского класса или другого?

Похоже, я не могу выполнить сопоставление с шаблоном на t: Class[MyParentClass] из-за типастирание, как показано ниже:

trait Product
trait PerishableProduct extends Product

class Fridge extends Product
class Banana extends PerishableProduct

def getProductType[P <: Product](implicit manifestP: Manifest[P]): Class[P] =
  manifestP.erasure.asInstanceOf[Class[P]]

val isPerishable = getProductType[Fridge] match {
  case x: Class[PerishableProduct] => true
  case _ => false
}
// ^^ warning: non variable type-argument PerishableProduct in type pattern
// Class[PerishableProduct] is unchecked since it is eliminated by erasure

Есть ли еще один трюк, который я пропустил?

Ответы [ 2 ]

10 голосов
/ 16 января 2012

Как насчет старого доброго отражения:

def isPerishable[P](implicit m: Manifest[P]): Boolean = 
  classOf[PerishableProduct].isAssignableFrom(m.erasure)

isPerishable[Fridge]   // false
isPerishable[Banana]   // true
5 голосов
/ 16 января 2012

Проблема в том, что вам нужно манифест, когда вы имеете дело с стиранием типов. Manifest предоставляет простой способ выполнить этот тест с помощью <: <. </p>

println( manifest[Fridge] <:< manifest[PerishableProduct] )
println( manifest[Banana] <:< manifest[PerishableProduct] )

Выше приведены прямые ссылки на типы, поэтому для обновления getProductType он будет использоваться.

def getProductType[P <: Product](implicit manifestP: Manifest[P]): Manifest[P] = manifestP
val isPerishable = getProductType[Fridge] <:< manifest[PerishableProduct]
println( isPerishable )
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...