如果“if”语句位于子句的末尾,为什么ruby中的条件语句和赋值会失败?

为什么最后一个语句(语句末尾的“if(tmp2 = foo)”)失败?

def foo;5;end # this one works if (tmp = foo) puts tmp.to_s end # why this one fails puts tmp2.to_s if (tmp2 = foo) #=> undefined local variable or method 'tmp2' for main:Object 

由于解析器的工作方式,它失败了。

从解析器的角度来看,变量tmp2从它首次被分配的代码中的点开始存在,直到它超出范围。 为此,无论何时(或者如果)实际执行赋值都是无关紧要的,只是当解析器看到赋值时(即它取决于代码中的赋值位置)。

编辑:要扩展该位:

解析器是否决定名称是局部变量还是方法调用。 解析器仅根据是否已经看到对该变量的赋值来做出该决定。 因此,当解析器在看到tmp2 = ...之前看到tmp2 = ... ,它决定在这里tmp2引用一个方法。 当代码的那部分实际执行时,它会尝试调用不存在的方法tmp2,这样你就会得到错误。

赋值运算符创建变量。 因此,当它看到’puts.temp2.​​to_s’时,它还不知道tmp2是什么。 如果您将代码更改为:

 def foo;5;end tmp2=1 puts tmp2.to_s if (tmp2 = foo) 

它会工作(并输出’5’)

 def foo; 5; end puts (tmp2 = foo) && tmp2 || nil