为什么我可以在Ruby中为自己分配一个未定义的变量,并得到nil?

为什么我可以在Ruby中为自己分配一个未定义的变量,并得到nil?,ruby,variable-assignment,internals,ruby-1.9.3,Ruby,Variable Assignment,Internals,Ruby 1.9.3,可能重复: 在Ruby中使用未定义的变量有一种“奇怪的现象”。是这样的: # irb session follows # foo # undefined local variable or method 'foo' bar # same for 'bar' foo = bar # still same for 'bar' foo = foo # nil - HUH? foo # is now set to nil!? 为什么我可以在Ruby中为自

可能重复:

在Ruby中使用未定义的变量有一种“奇怪的现象”。是这样的:

# irb session follows
#
foo        # undefined local variable or method 'foo'
bar        # same for 'bar'
foo = bar  # still same for 'bar'
foo = foo  # nil - HUH?
foo        # is now set to nil!?
为什么我可以在Ruby中为自己分配一个未定义的变量,并得到
nil

注意,我在这里使用的是Ruby 1.9.3。我不确定在其他版本中这可能是真的


(感谢Gary Bernhardt在他的文章中演示了这一点。)

Nil在Ruby中具有魔力,因为它认为一切都是对象。实际上有一个单例nil对象被赋值。你什么时候做的

foo = bar

“foo”变量突然出现,并将神奇的nil对象作为值。在你做赋值之前,Ruby没有办法“知道”什么是foo(它是一个变量吗?一个方法调用?),但是一旦你做了赋值,它就开始把它当作一个变量来处理。

事实上,bar没有定义并不是最有趣的部分,因为举例来说,赋值甚至不需要尝试

if false
  foo = 1
end

将foo设置为nil。据我所知,局部变量的作用域是静态确定的,因为它是在不实际运行代码的情况下确定的,仅通过分析它。Ruby认为赋值可能发生,因此它创建局部变量并将其设置为nil。请参见

大概,
foo=foo
分两步进行评估。第一个用默认值“声明”变量,第二个将其赋值给它自己。好吧,
foo=foo
也可以在没有任何先前语句的情况下工作。它确实可以,原因也是一样的。nil不是问题所在,它只是一个未定义值的占位符。问题是赋值,一旦Ruby看到赋值,它“决定”将“=”左边的标记视为变量。@theglauber,这并不能完全解释
foo=foo
。在
foo=bar
的情况下,如果foo和bar都未定义,则仍会引发异常。
foo=foo
工作的奇怪情况是由于ruby解释器在表达式求值之前执行初始化。基本上,在左手边,foo被初始化为nil;然后,当解释器到达表达式求值以执行赋值时,右侧的foo已经初始化。更好的是,if语句中要赋值的变量不必定义:
foo=wat if false
来自post的链接已失效