我有一个与scala implicit
相关的初学者问题:
class Box[T](implicit tag: ClassTag[T]) {
var value = None: Option[Any]
def pickValueUsingTypeOfT : Unit = {
val list = List("string", 1, new myClass(1D) )
println(s"type of has type arguments $tag")
//value = Some ( find right element from the 'list' )
}
}
class myClass(double: Double) {}
object Setter {
def main(args: Array[String]) {
val n: Box[String] = new Box[String]
n.pickValueUsingTypeOfT
}
}
目标是根据value
的类型设置T
。
答案 0 :(得分:1)
你不需要反思这样的解决方案。您需要typeclass(例如Numeric
)。
trait Foo[T] {
def aProp: String
def aFun(v: T): Int
}
object Foo {
// default instances
object StrFoo extends Foo[String] {
// for T = String
val aProp = "Bar"
def aFun(v: String) = v.length
}
object LongFoo extends Foo[Long] {
val aProp = "Lorem"
def aFun(v: Long) = v.toInt
}
}
所以你的功能可以定义如下。
def pickValueUsingTypeOfT[T](implicit resolved: Foo[T]) = ???
然后它可以用于默认实例:
pickValueUsingTypeOfT[String].aProp
pickValueUsingTypeOfT[Long].aFun(123L)
如果它被调用了不支持的类型,编译器会发现这个问题并帮助你(比运行时反射更好):
pickValueUsingTypeOfT[Byte] // compiler error
可以定义额外的实例。
val localV = "value"
implicit val byteFoo: Foo[Byte] = new Foo[Byte] {
def aProp: String = localV
def aFun(v: Byte) = v.toInt * 10
}
pickValueUsingTypeOfT[Byte].aFun(456.toByte)
// now is ok with byteFoo