gpt4 book ai didi

ruby - 了解 Ruby 闭包

转载 作者:数据小太阳 更新时间:2023-10-29 07:46:41 25 4
gpt4 key购买 nike

我试图更好地理解 Ruby 闭包,但我遇到了这个我不太理解的示例代码:

def make_counter
n = 0
return Proc.new { n = n + 1 }
end

c = make_counter
puts c.call # => this outputs 1
puts c.call # => this outputs 2

当我调用 c = make_counter 时,有人能帮我理解上面代码中实际发生了什么吗?在我看来,这就是我认为正在发生的事情:

Ruby 调用 make_counter 方法并返回一个 Proc 对象,其中与 Proc 关联的代码块将为 { n = 1 } 。当执行第一个c.call 时,Proc 对象将执行与其关联的 block ,并返回n = 1。但是,当执行第二个c.call时,Proc对象不还是会执行与其关联的block,还是{ n = 1 } 吗?我不明白为什么输出会变成 2。

也许我根本不理解这一点,如果您能就 Ruby 中实际发生的事情提供一些说明,那将会很有帮助。

最佳答案

make_counter 被调用时, block 不会被评估。当您通过 c.call 调用 Proc 时,将评估并运行该 block 。因此,每次运行 c.call 时,都会计算并运行表达式 n = n + 1。 Proc 的绑定(bind)将导致 n 变量保留在范围内,因为它(本地 n 变量)首先在 Proc 闭包之外声明。因此,n 将在每次迭代中不断递增。

进一步澄清:

  • 定义 Proc(或 lambda)的 block 不会在初始化时求值 - 其中的代码完全如您所见完全卡住。
  • 好的,代码实际上是“评估”的,但不是为了更改卡住的代码。相反,它会检查当前在范围内的任何变量,这些变量正在 Proc 的代码块的上下文中使用。由于 n 是局部变量(如前一行定义的那样),并且在 Proc 中使用,因此它在绑定(bind)中被捕获并随行。
  • 当在 Proc 上调用 call 方法时,它将在已捕获的绑定(bind)上下文中执行“卡住”代码。所以原本赋值为0的n被加1,再次调用时,同样的n又会加2,以此类推……

关于ruby - 了解 Ruby 闭包,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14888247/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com