ruby - 名称错误 : undefined - have parsing rules for local variables changed in Ruby 2. 1.2?

标签 ruby parsing variable-assignment local-variables guard-clause

我得到 NameError: undefined local variable or method with ruby​​ 2.1.2

正如在 this question 中观察到的那样, 表达式如:

bar if bar = true

引发未定义的局部变量错误(前提是 bar 之前未定义),因为 bar 在分配之前被解析器读取。而且我相信以前用这个表达式没有什么区别:

bar if bar = false

两者之间的区别在于主体是否被求值,但如果遇到未定义的局部变量会在求值条件之前立即引发错误,那应该无关紧要。

但是当我在 Ruby 2.1.2 上运行第二个代码时,它没有引发错误。以前也是这样吗?如果是这样,那么解析讨论的内容是什么?如果没有,Ruby 规范是否改变了?有什么引用吗?它在 1.8.7、1.9.3 等版本中做了什么?

最佳答案

bar 是否定义没有区别。在这两种情况下,bar 在正文中都是未定义的。然而,在后一种情况下, body 永远不会被评估,因此无关紧要。您永远不会解析名称 bar,因此在名称解析期间您永远不会遇到错误。

局部变量是在解析赋值时定义的。 它们在执行时被初始化

变量被单元化是完全没问题的。在这种情况下,它只会评估为 nil:

if false
  bar = 42
end

bar
# => nil

但是,如果变量是undefined,那么 Ruby 不知道一个 bare word 是一个局部变量还是一个 receiverless argumentless 消息发送:

foo
# NameError: undefined local variable or method `foo'
#                                     ^^^^^^^^^
# Ruby doesn't know whether it's a variable or a message send

比较:

foo()
# NoMethodError: undefined method `foo'
# ^^^^^^^^^^^^^

self.foo
# NoMethodError: undefined method `foo'
# ^^^^^^^^^^^^^

现在在一起:

foo()
# NoMethodError: undefined method `foo'

self.foo
# NoMethodError: undefined method `foo'

foo
# NameError: undefined local variable or method `foo'

if false
  foo = 42
end

foo
# => nil

foo = :fortytwo

foo
# => :fortytwo

在这种特殊情况下,问题在于表达式被解析的顺序(以及变量定义的顺序)与顺序匹配表达式在其中执行

赋值首先执行,这会让您假设 bar 将在正文中定义。但它不是,因为正文首先被解析,因此一个我不知道这是一个方法还是一个变量节点被插入到语法树中< em>在作业被看到之前。

但是,如果该节点从未被解释过,即条件为假,那么就不会发生任何坏事。

关于ruby - 名称错误 : undefined - have parsing rules for local variables changed in Ruby 2. 1.2?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25306902/

相关文章:

ruby-on-rails - rspec spec 自动逻辑分组(按 "tags")

javascript - 使用 Javascript 解析 XML(在 Google Scripts 中)

ruby 需要很慢

ruby-on-rails - Vagrant 工作流程 - vagrant ssh、vagrant destroy、vagrant up 命令

java - Java/Groovy 中的电子表格解析器

c++ - 使用getline解析和存储变量

javascript - 我对这个条件 "value || value"赋值的理解正确吗?

C++获取字节数组中字符串后的短数字

r - 如何在函数内访问分配给函数结果的变量名?

ruby-on-rails - database.yml 中应该包含什么以在没有数据库的情况下使用 rails?