这似乎在斯卡拉2.11.x和2.12.x,一点点我自己都感到惊讶的工作。
scala> import scala.reflect.ClassTag
import scala.reflect.ClassTag
scala> class Boxed[T <: AnyVal] { def apply[R <: AnyRef]()(implicit conv: T => R, tag: ClassTag[R]) = tag.runtimeClass }
defined class Boxed
scala> def boxedClass[T <: AnyVal] = new Boxed[T]
boxedClass: [T <: AnyVal]=> Boxed[T]
scala> boxedClass[Int]()
res5: Class[_] = class java.lang.Integer
scala> boxedClass[Double]()
res6: Class[_] = class java.lang.Double
它通过固定T
到你想要的盒装类的类型,然后寻找的T
的类型R
那就是AnyRef
子类型转换。然后你拿ClassTag[R]
,你有你正在寻找的课程。
票友的解决办法是:
sealed trait BoxedClass[T <: AnyVal] {
type R <: AnyRef
def clazz: Class[R]
}
object BoxedClass {
import scala.reflect.ClassTag
implicit def mkBoxedClass[T <: AnyVal, R0 <: AnyRef](
implicit
conv: T => R0,
tag: ClassTag[R0]) =
new BoxedClass[T] {
type R=R0
val clazz = tag.runtimeClass.asInstanceOf[Class[R]]
}
}
def boxedClass[T <: AnyVal](implicit b: BoxedClass[T]): Class[b.R] = b.clazz
用法:
scala> boxedClass[Int]
res0: Class[Integer] = class java.lang.Integer
scala> boxedClass[Long]
res1: Class[Long] = class java.lang.Long
另外请注意,这是不行的了,如果你定义或导入任何其他隐式转换Int
扩展为AnyRef
。
很明显,你不打算使用.asInstanceOf生产?这是不安全的。你尝试使用模式匹配吗? – Pavel
@Pavel我没有在生产中使用这些代码。我只是问问。我不知道模式匹配在这里可以起到什么作用。如果您有任何想法,请提供您的答案。 – mixel
有'Int.box',但我不确定你想要实现什么。 – rethab