4

为什么local_variables返回尚未赋值的局部变量(调用后赋值local_variables)?

a = 2
@aa = 1
# a = b # this will raise an error.
puts "local: #{ local_variables }"
puts "instance: #{ instance_variables }"

b = 2
@bb = 2
puts "local: #{ local_variables }"
puts "instance: #{ instance_variables }"

结果:

local: [:a, :b]
instance: [:@aa]
local: [:a, :b]
instance: [:@aa, :@bb]

我期望的是像 那样的行为instance_variables,它只返回在那一刻已经分配的变量。

4

2 回答 2

1

Ruby在编译时创建局部变量。实例变量明确地绑定到实例并且可以很容易地访问。但是,b可能是:

  1. 方法调用
  2. self.b
  3. 局部变量b

在此处查看Brian Candler 的回复(Google 缓存)。这也是为什么你不能在运行时用 eval 创建局部变量的原因。

于 2013-03-28T09:14:55.960 回答
1

Kernel#local_variables列出当前范围内的所有局部变量,包括那些可能尚未赋值的局部变量。MRI解析每个作用域中的局部变量并在代码本身(puts local_variables.inspect如下所示)运行之前声明它们,因此即使在local_variables定义这些变量之前调用它们也会显示它们

但请注意,在调用时defined?仍会返回nil尚未分配给的变量local_variables

$ cat /tmp/locals
#!/usr/bin/env ruby

a = 5
puts local_variables.inspect
puts defined?(a)
puts (defined?(b) || "[undefined]")
b = 10
puts defined?(b)

def foo
  c = 15
  puts local_variables.inspect
  d = 20
end
foo

$ ruby /tmp/locals
[:a, :b]
local-variable
[undefined]
local-variable
[:c, :d]
于 2013-03-28T08:42:27.367 回答