为什么这个关闭不起作用?

时间:2015-08-26 19:10:34

标签: ruby

在下面的示例中,我原以为close_over_me可以通过闭包对返回的对象使用。

但显然事实并非如此。

为什么不呢?

此外,有哪些选项可以使代码按预期工作(即返回值1而不是错误)?

def test_closure(close_over_me: 1)
  Object.new.tap do |x|
    def x.captured_var
      close_over_me
    end
  end
end

o = test_closure
o.captured_var # NameError: undefined local variable or method `close_over_me' for #<Object:0x007fb46b41a718>

2 个答案:

答案 0 :(得分:5)

原因是def关键字定义了一个新范围。

要解决此问题,您可以改为使用Object#define_singleton_method

def test_closure(close_over_me: 1)
  Object.new.tap do |x|
    x.define_singleton_method(:captured_var) do
      close_over_me
    end
  end
end

o = test_closure
o.captured_var # => 1

答案 1 :(得分:3)

这就是所谓的“范围门”。关键字def / class / module将所有局部变量推出范围。

如果没有这些,你必须想出一种修补方法。