如果该方法是infix并且是右关联的,为什么Scala会为一个按名字调用参数评估参数? [英] Why does Scala evaluate the argument for a call-by-name parameter if the method is infix and right-associative?

查看:91
本文介绍了如果该方法是infix并且是右关联的,为什么Scala会为一个按名字调用参数评估参数?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

据我了解,方法的call-by-name参数,当将相应的参数表达式传递给该方法时,将不对其求值,而仅在(如果)在方法主体中使用该参数的值时,才对其求值.

As I understood call-by-name parameters of a method, the corresponding argument expression will not be evaluated when passing it to the method, but only when (and if) the value of the parameter is used in the method body.

但是,在下面的示例中,这仅在前两个方法调用中适用,而在第三个方法调用中则不适用,尽管这仅是第二种情况的语法变体!

In the following example, however, this is only true in the first two method calls, but not in the third one, although it should be a merely syntactical variation of the second case!?

为什么在第三个方法调用中对自变量表达式求值?

Why is the argument expression evaluated in the third method call?

(我使用Scala 2.11.7测试了此代码)

(I tested this code using Scala 2.11.7)

class Node(x: => Int)

class Foo {
  def :: (x: =>Int) = new Node(x)  // a right-associative method
  def !! (x: =>Int) = new Node(x)  // a left-associative method
}

// Infix method call will not evaluate a call-by-name parameter:
val node = (new Foo) !! {println(1); 1}
println("Nothing evaluated up to here")

// Right-associative method call will not evaluate a call-by-name parameter:
val node1 = (new Foo).::({println(1); 1})
println("Nothing evaluated up to here")

// Infix and right-associative method call will evaluate a call-by-name parameter - why??
val node2 = {println(1); 1} ::(new Foo)  // prints 1
println("1 has been evaluated now - why??")

推荐答案

只要提及名字参数,就对其进行评估. 规范说,这种右关联运算符方法调用的评估方式如下:

By-name arguments are evaluated whenever they are mentioned. The spec says that right-associative operator method calls are evaluated like this:

a op_: b

对以下对象不满意:

{ val someFreshName = a; b.op_:(someFreshName) }
//                   ↑↑↑
// Eval happens here ↑↑↑

这篇关于如果该方法是infix并且是右关联的,为什么Scala会为一个按名字调用参数评估参数?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆