【问题标题】:How does a new IRB session get its variable scope?新的 IRB 会话如何获得其可变范围?
【发布时间】:2012-05-26 15:13:20
【问题描述】:

IRB 是一种在 Ruby 中玩耍和测试事物的好方法。也可以使用脚本进行一些设置,如下所示:

require 'irb'

class Pirate
  def greet
    puts "Arrrrr, nice to meet ya"
  end
end

IRB.start # You can now instantiate Pirate in IRB

但是,我不清楚的一件事是执行此操作时的变量范围。如果我在IRB.start 之前添加这些行:

smithy     = Pirate.new
@blackbard = Pirate.new

...@blackbeard 将在 IRB 中可用,但引用 smithy 将得到 undefined local variable or method 'smithy' for main:Object

为什么?

【问题讨论】:

    标签: ruby scope irb


    【解决方案1】:

    用于评估代码的Binding 设置在irb/workspace.rb:51 中(我在这里指的是Ruby 1.9.3 rev 35410):

    @binding = eval("def irb_binding; binding; end; irb_binding",
                    TOPLEVEL_BINDING,
                    __FILE__,
                    __LINE__ - 3)
    

    这意味着您的 IRB 会话与顶级方法中的代码在相同的上下文中运行。观察:

    puts "Outer object ID: %d" % self.object_id
    puts "Outer binding: " + binding.inspect
    smithy     = Pirate.new
    @blackbard = Pirate.new
    
    def test
      puts "Inner object ID: %d" % self.object_id
      puts "Inner binding: " + binding.inspect
      p @blackbard
      p smithy
    end
    test
    

    输出:

    Outer object ID: 13230960
    Outer binding: #<Binding:0x00000001c9aee0>
    Inner object ID: 13230960
    Inner binding: #<Binding:0x00000001c9acd8>
    #<Pirate:0x00000001c9ada0>
    /test.rb:18:in `test': undefined local variable or method `smithy' for main:Object (NameError)
        ...
    

    请注意,对象上下文 (self) 在函数内部和外部都是相同的。这是因为每个顶级方法都添加到全局 main 对象中。

    还要注意方法内部和外部的绑定是不同的。在 Ruby 中,每个方法都有自己的名称范围。这就是为什么您不能从 IRB 内部访问本地名称,而您可以访问实例变量的原因。

    说实话,IRB 并不是 Ruby 软件中最出色的部分。我通常使用Pry 来处理这种东西,你可以使用它:

    require 'pry'
    binding.pry
    

    并拥有一个可以访问当前局部变量的会话。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-03-31
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2023-03-04
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多