当为具有已删除参数的类型合成 ClassTag 时,如何取消隐藏未选中的警告?



类型参数上的模式匹配T引发未选中的警告

scala> def f[T](v: List[Any]): List[T] = v.collect { case x: T => x }
^
warning: abstract type pattern T is unchecked since it is eliminated by erasure
def f[T](v: List[Any]): List[T]

哪个可能会尝试用ClassTag解决

scala> def f[T: scala.reflect.ClassTag](v: List[Any]): List[T] = v.collect { case x: T => x }
def f[T](v: List[Any])(implicit evidence$1: scala.reflect.ClassTag[T]): List[T]

解决了基于类的简单类型的警告

scala> f[String](List(42, "a"))
val res7: List[String] = List(a)

但是现在,即使对于在运行时擦除了组件的参数化类型的类型,未选中的警告也会被隐藏

f[List[String]](List(List(42)))
val res9: List[List[String]] = List(List(42)) // oops!

在后一种情况下,我们如何继续发出未经检查的警告?

Scala 3 用TypeTest替换了ClassTag,或者它的速记Typeable,当我们尝试检查的不仅仅是一个类型的类组件时,它会发出警告

scala> def f[T: scala.reflect.Typeable](v: List[Any]): List[T] = v.collect { case x: T => x }
def f[T](v: List[Any])(implicit evidence$1: scala.reflect.Typeable[T]): List[T]
scala> f[String](List(42, "a"))
val res0: List[String] = List(a)
scala> f[List[String]](List(List(42)))
1 |f[List[String]](List(List(42)))
|                               ^
|               the type test for List[String] cannot be checked at runtime
val res1: List[List[String]] = List(List(42))

正如更聪明的人所说

TypeTag不再存在

型式试验ClassTag.unapply不合理,不应使用

相反,我们现在有TypeTest:lampepfl/dotty#7555

最新更新