5.5 方法返回类型推演

除了推演变量的类型,Scala也会尝试推演方法返回值的类型。不过,这有个陷阱,推演会依赖于方法如何定义。如果用等号(=)定义方法,Scala就可以推演返回类型。否则,它就假设方法是一个void方法。我们看个例子:

SensibleTyping/Methods.scala

  1. def printMethodInfo(methodName: String) {
  2. println("The return type of " + methodName + " is" +
  3. getClass().getDeclaredMethod(methodName, null).getReturnType().
  4. getName())
  5. }
  6. def method1() { 6 }
  7. def method2() ={ 6 }
  8. def method3() = 6
  9. def method4 : Double = 6
  10. printMethodInfo("method1")
  11. printMethodInfo("method2")
  12. printMethodInfo("method3")
  13. printMethodInfo("method4")

方法method1()是按照正常方式定义的,提供一个方法名,括号里是参数列表,大括号里是方法体。然而,这种方式并不是地道的Scala定义方法的方式。方法method2()是用等号定义的。二者唯一的差别就是等号;不过,在Scala里,这可是意义重大。Scala推演method1()为一个void方法,而method2()则返回一个Int(Java的int)。结果如下:

  1. The return type of method1 is void
  2. The return type of method2 is int
  3. The return type of method3 is int
  4. The return type of method4 is double

如果方法定义或方法体很小,能够浓缩为一个表达式,就可以省去{},就像method3()一样。对仅仅执行最小检查的简单的getter和setter而言,这点非常有用。

通过提供所需类型,还可以改写Scala默认的类型推演,就像method4()一样。这里将method4()的返回类型声明为Double,也可以声明为UnitShortLongFloat,等等,只要类型与方法执行的返回结果兼容即可。如果不兼容,比如我们声明method4()的返回类型为String,那么Scala会报出一个类型不匹配的编译时错误。

总的来说,使用=,让Scala推演方法的类型会好一些。这样可以少担心一件事,让构建良好的类型推演为我们服务。