代码之家  ›  专栏  ›  技术社区  ›  sandre89

Ruby:使用instance\u eval(&lambda)和instance\u eval{lambda.呼叫}

  •  0
  • sandre89  · 技术社区  · 5 年前

    我想叫一个lambda改变它的自我价值。为了寻找它,我来到了 instance_exec ,本该完成任务的。

    然而,经过1个多小时的学习,我发现这个行为我无法解释:

    class Dummy
    
      class << self
    
        attr_accessor :my_lambda
    
      end
    
      self.my_lambda = proc { self }
    
      def test
        self.class.my_lambda.call
      end
    
      def test1
        instance_eval(&self.class.my_lambda)
      end
    
      def test2
        instance_eval { self.class.my_lambda.call }
      end
    
    end
    
    Dummy.new.test
    => Dummy # I was expecting this, returns the class, lexical scope (where `self` was defined)
    
    Dummy.new.test1
    => #<Dummy:0x00007fe982f8b678> # I was expecting this, `self` changed to the receiver of `instance_eval`, which is the instance, so `self` returned the instance.
    
    Dummy.new.test2
    => Dummy # I can't understand this, at all. Why isn't it the same as test1?
    

    那么,为什么我们从中得到不同的结果呢 instance_eval(&self.class.my_lambda) instance_eval { self.class.my_lambda.call } ?

    另外,既然我们现在的主题是叫Lambdas。。。如果我将类级别变量更改为:

    self.my_lambda = lambda { self }
    

    那么虚拟新试验1引发异常 ArgumentError: wrong number of arguments (given 1, expected 0) 实例评估(&U);自我类我的lambda)

    1 回复  |  直到 5 年前
        1
  •  2
  •   sandre89    5 年前

    令人惊讶的是,在写了这么长的问题之后,我竟然在一分钟内自己回答了这个问题。我需要一只橡皮鸭。不管怎样。

    我误解了 instance_eval

    所以,给定的块 #test2 instance_eval { self.class.my_lambda.call } self 设置为实例, 但是 lambda仍然在它里面被调用,这是不变的 是的

    然而,在 #test1 & 将进程更改为块,然后将其传递给 ,所以是proc自己的主体用 自己 改变。

    推荐文章