Scala入门-本地类型推断(Local Type Inference)
本地类型推断(Local Type Inference)
Scala具有一个内置的类型推断机制,它允许程序员省略特定的类型注解。举个例子,由于编译器可以从变量的初始化表达式推断出它的类型,所以通常没必要指定一个变量的类型。由于方法的返回类型对应的是方法体的类型,可以由编译器推断出来,所以方法的返回类型也可以省略。
下面是一个例子:
object InferenceTest1 extends App {
val x = 1 + 2 * 3 // the type of x is Int
val y = x.toString() // the type of y is String
def succ(x: Int) = x + 1 // method succ returns Int values
}
对于递归方法,编译器无法推断出结果的类型。下面的程序就是由于这个原因而编译失败:
object InferenceTest2 {
def fac(n: Int) = if (n == 0) 1 else n * fac(n - 1)
}
当多态方法被调用或者泛型类被实例化时,类型参数也不是必须指定的。Scala编译器将会从上下文环境以及传入方法/构造函数的实际参数的类型推断出缺失的类型参数。
下面是一个例子:
case class MyPair[A, B](x: A, y: B);
object InferenceTest3 extends App {
def id[T](x: T) = x
val p = MyPair(1, "scala") // type: MyPair[Int, String]
val q = id(1) // type: Int
}
上面程序的最后两行与下面的代码是等价的,下面的代码将需要推断的类型都变成显示声明的:
val x: MyPair[Int, String] = MyPair[Int, String](1, "scala")
val y: Int = id[Int](1)
在某些情况下依赖Scala的类型推断机制是很危险的,例如下面的程序:
object InferenceTest4 {
var obj = null
obj = new Object()
}
这个程序将会编译失败,因为对变量obj推断出来的类型是Null。由于Null类型的值只能是null,是不可能让这个变量指向另一个值的。
参考资料
本文译自Tour Of Scala – Local Type Inference
上一篇:Scala之旅-多态方法