Scala:val foo =(arg:Type)=> {...}与def(arg:Type)= {...}

时间:2012-06-05 16:35:33

标签: function scala runtime state immutability

this thread

相关

我仍然不清楚这两个定义之间的区别:

val foo = (arg: Type) => {...}
def(arg:Type) = {...}

据我所知:

1)val版本在编译时绑定一次 创建单个Function1实例
可以作为方法参数传递

2)def版本在每次通话时重新绑定 每次调用创建的新方法实例。

如果上述情况属实,那么为什么在要执行的操作不依赖于运行时状态的情况下会选择def版本?

例如,在servlet环境中,您可能希望获取连接客户端的IP地址;在这种情况下,您需要使用def,因为在编译时没有连接的客户端。

另一方面,你经常在编译时知道要执行的操作,并且可以使用不可变的val foo = (i: Type) => {...}

根据经验,当存在运行时状态依赖时,是否应该只使用defs?

感谢您澄清

1 个答案:

答案 0 :(得分:4)

我不完全清楚运行时状态依赖的含义。 valdef都可以关闭它们的词法范围,因此无限制。那么Scala has been asked and answered before中的方法(def s)和函数(作为val s)之间有什么区别?

您可以参数化def

例如:

object List {

  def empty[A]: List[A] = Nil     //type parameter alllowed here

  val Empty: List[Nothing] = Nil  //cannot create a type parameter
}

然后我可以打电话:

List.empty[Int]

但我必须使用:

List.Empty: List[Int]

但当然还有其他原因。如:

def是JVM级别的方法

如果我要使用这段代码:

trades filter isEuropean

我可以选择isEuropean的声明为:

val isEuropean = (_ : Trade).country.region = Europe

def isEuropean(t: Trade) = t.country.region = Europe

后者避免在声明点创建对象(对于函数实例),但不在使用点。 Scala正在为使用点的方法声明创建一个函数实例。如果我使用_语法,则更清楚。

但是,在下面的代码中:

val b = isEuropean(t)

...如果isEuropean被声明为def,则不会创建此类对象,因此代码可能更高效(如果在非常紧密的循环中使用,其中每个最后纳秒具有临界值)