如何强制编译时函数的参数在Scala中是特定类型的?

时间:2016-12-19 22:35:34

标签: java scala functional-programming

当我们只知道对象类型是Any时,有没有办法强制将函数参数的编译类型设置为函数签名中定义的期望类型?让我用一个简单的例子来证明它。

鉴于我们已经定义了以下三个函数:

def writeInt(value: Int): Unit { ... }

def writeString(value: String): Unit { ... }

def get(name: String): Any = { ... }

如何在不强制程序员在其程序中引用writeInt函数的情况下成功编译以下代码,以明确说明get返回应该使用.asInstanceOf[Int]

writeInt(get("dividend").asInstanceOf[Int]) // this works...
writeInt(get("dividend"))                   // but this does not :(

由于get可能会返回Any对象(可能是Int以及String),因此在 Scala中有一种优雅的解决方法没有丑陋的.asInstanceOf[Int]符号?

请注意,在程序的其他部分,我希望能够使用相同的函数分别编写此代码,而无需再次键入.asInstanceOf[String]

writeString(get("name").asInstanceOf[String]) // this works...
writeString(get("name"))                      // but this does not :(

基本上,我知道get("dividend")会返回Intget("name")会返回String。但是,如何让编译器在没有太多杂乱的情况下知道呢?

1 个答案:

答案 0 :(得分:2)

您可以使用write方法的包装器。

def writeAny(a: Any): Unit = a match {
  case s: String => writeString(s)
  case i: Int    => writeInt(i)
}

更好的解决方案是让get()方法返回Either[String,Int]。然后你的代码可以这样做:

get(str).fold(writeString, writeInt)

作为一般规则,应尽可能避免使用Any