我不喜欢Scala isInstanceOf和asInstanceOf方法 - 它们很长并且asInstanceOf可以抛出异常所以我们需要在几个中使用它。更好的方法是使用模式匹配:Scala: How do I cast a variable?但是对于非常简单的操作,它也可能相对较长。在C#中,我们有'is'和'as'运算符,所以我想在Scala中实现隐式定义。我的代码看起来像这样:
scala> class TypeCast(x:Any){
| def is[T](t:Class[T]) = t.isInstance(x)
| def as[T](t:Class[T]):Option[T] = if(t.isInstance(x)) Option(t.cast(x)) else None
| }
defined class TypeCast
scala> implicit def TypeCastID(x:Any)=new TypeCast(x)
TypeCastID: (x: Any)TypeCast
scala> 123 as classOf[String]
res14: Option[String] = None
scala> "asd" as classOf[String]
res15: Option[String] = Some(asd)
它有一个优点 - 实现null-object模式但也有缺点:
需要使用classOf [T]操作符 - 它太长了
与这种简单操作的隐式def连接的开销
所以没有实际的理由使用它。 我想知道有没有办法实现它而不需要使用classOf [T]?
答案 0 :(得分:10)
嗯,你可以在你在TypeCast类中制作的def中缩短它。因此,您可以仅依靠类型而不是为它提供参数。这会使它缩短很多。作为一个例子,这可能看起来像:
class TypeCast(x : Any) {
def is[T : Manifest] = manifest.erasure.isInstance(x)
def as[T : Manifest] : Option[T] = if (manifest.erasure.isInstance(x)) Some(x.asInstanceOf[T]) else None
}
未来的电话可能如下:
scala> 123.as[String]
res0: Option[String] = Some(123)
scala> class A; class B extends A
defined class A
defined class B
scala> new B
res1: B
scala> res1.is[Int]
res2: Boolean = false
scala> res1.as[Int]
res3: Option[Int] = None
更新:我添加了清单以避免类型检查错误