2

我想实现一个包含类型参数的子类,并编写根据参数是否符合参数而表现不同的函数的实现。

考虑:

import scala.reflect.runtime.universe;

trait Lover {
    def love( amour : Any ) : String
}

class TypedLover[MY_TYPE]( implicit val myTypeTag : universe.TypeTag[MY_TYPE] ) extends Lover {
    def love( amour : Any ) : String =
        if ( ??? ) "You are totally my type." else "Nope, sorry, not my type."
}

我将在这里使用什么条件?[更新:如果函数参数amour符合 MY_TYPE,则条件应返回 true,否则返回 false。]

非常感谢您的帮助。

4

4 回答 4

3
class TypedLover[A](implicit tt: TypeTag[A]) extends Lover {
  def love(amour: Any) =
    if (tt.tpe =:= typeOf[String]) "You are totally my type."
    else "Nope, sorry, not my type."
}

scala> new TypedLover[String].love(null)
res2: String = You are totally my type.

scala> new TypedLover[Int].love(null)
res3: String = Nope, sorry, not my type.

For a detailed introduction in how a TypeTag works, see this question: Scala: What is a TypeTag and how do I use it?

于 2013-03-07T06:02:57.327 回答
2

我想你想要这样的东西:

trait Lover {
  def love( amour : Any ) : String
}

class TypedLover[A : ClassTag] extends Lover {
    def love(amour : Any) = {
        if (implicitly[ClassTag[A]].runtimeClass == amour.getClass) {
                "Totally my type."
            } else {
                "Sorry, you are not my type."
            }
    }
}

val tl = new TypedLover[String]
tl.love(1) // res0: String = Sorry, you are not my type.
tl.love("Hello") //res1: String = Totally my type.

请注意,如果要捕获子类型,您可以使用诸如isAssignableFrom代替的方法。==

于 2013-03-07T10:13:28.133 回答
0

Scala 有一种使用Manifest类来解决类型擦除的方法。我的要点的链接说明了用法 - https://gist.github.com/anoopelias/4462155

于 2013-03-07T04:56:13.017 回答
0

这是我能做到的最好的。它不会捕获真正的运行时类型信息,这正是我想要的,但它至少在编译时捕获了使用点已知的类型信息:

import scala.reflect.runtime.universe._

trait Lover {
  def love[ T : TypeTag ]( amour : T ) : String;
}

class TypedLover[MY_TYPE : TypeTag] {
  def love[ T : TypeTag ]( amour : T ) : String =
    if ( implicitly[TypeTag[T]].tpe <:< implicitly[TypeTag[MY_TYPE]].tpe )
      "You are totally my type."
    else
      "Nope, sorry, not my type."
}

以下是它的工作原理:

scala> val intLover = new TypedLover[Int]
intLover: TypedLover[Int] = TypedLover@2d4cadc4

scala> intLover.love(7)
res2: String = You are totally my type.

scala> intLover.love("Hello")
res3: String = Nope, sorry, not my type.

scala> val stringLover = new TypedLover[String]
stringLover: TypedLover[String] = TypedLover@1f7c9157

scala> stringLover.love(7)
res4: String = Nope, sorry, not my type.

scala> stringLover.love("Hello")
res5: String = You are totally my type.

但它仍然无法捕获实际的运行时类型信息:

scala> val stringInAnyRef : Any = "Hello"
stringInAnyRef: Any = Hello

scala> stringLover.love( stringInAnyRef )
res7: String = Nope, sorry, not my type.

它并不完美,但它是迄今为止我所拥有的最好的。

于 2013-03-26T03:04:03.297 回答