我想要一种退出Begin/End块的方法,同时仍将其结果分配给的变量赋值。

def foo
  @foo ||= begin
    puts "running"

    return "leaving early" if true # would be some sort of calculation

    # Other calculations
  end
end

我希望发生什么
> foo
running
=> leaving early
> foo
=> leaving early

实际发生了什么
> foo
running
=> leaving early
> foo
running
=> leaving early

该代码无效,因为return退出整个方法而未设置@foo。使用breaknext仅在循环中有效。开始中是否有任何事情可以阻止我的思维方式?

目前可以做到的方式,但我希望避免:
  • 在begin块内分配变量并返回
  • 将begin块的其余部分放在if语句
  • 在开始块
  • 之前执行计算

    关于突破规则,似乎有很多相关的问题,但是我找不到一个能回答这个特定版本的问题(也许是因为这不可能)。

    最佳答案

    我认为,只要将所有逻辑放入自己的方法中,您就可以省去很多麻烦:

    def foo
      @foo ||= compute_foo
    end
    
    def compute_foo
      puts "running"
    
      return "leaving early" if true # would be some sort of calculation
    
      # Other calculations
    end
    

    这将计算与备忘录分离开来,从而使测试和推理变得更加容易,并且这是Ruby和其他语言中相当普遍的设计模式。

    当然,有多种方法可以满足您的要求。最明显的解决方案是立即调用匿名proc:
    def foo
      @foo ||= (proc do
        puts "running"
    
        next "leaving early" if true # would be some sort of calculation
    
        # Other calculations
      end)[] # or .call or .()
    end
    

    但是您当然不会对自己或该代码的任何将来的维护者有所帮助。

    关于ruby - 尽早突破起点/终点,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/55735695/

    10-12 03:08