[英]Ruby loop local variables and inmutability
I have the following code: 我有以下代码:
# Assuming each element in foo is an array.
foo.each do |bar|
zaz = bar.first
# Other code using zaz, but not modifying it.
end
Will zaz
local variable be modified on each iteration inside this loop, making it mutable? 是否会在此循环内的每次迭代中修改
zaz
局部变量,使其可变? I am not sure about the behavior of Ruby here. 我不确定Ruby的行为。
It depends on the code before the loop, really. 实际上,这取决于循环之前的代码。
If that is all the code, then zaz
is a block-local variable, and a new zaz
variable will be created every time the loop body is evaluated. 如果这就是全部代码,则
zaz
是块局部变量,并且每次评估循环体时都将创建一个新的 zaz
变量。
If, however, there is a zaz
local variable in the surrounding scope, then zaz
is a free variable in the block, and since block scopes nest in their surrounding scope, the existing zaz
variable outside the block will be re-assigned over and over again, every time the block is evaluated. 但是,如果周围范围中有
zaz
局部变量,则zaz
是块中的自由变量,并且由于块范围嵌套在其周围范围中,因此,将zaz
重新分配该块外部的现有zaz
变量再次,每次评估块。
You can ensure that zaz
is always treated as a block-local variable and never looked up in the surrounding scope, by explicitly declaring it as a block-local variable in the block's parameter list: 通过在块的参数列表中明确将其声明为块局部变量,可以确保
zaz
始终被视为块局部变量,并且永远不会在周围的范围中查找:
foo.each do |bar; zaz|
zaz = bar.first
end
Note, however, that your code only makes sense IFF your code is impure and mutable: 但是请注意,你的代码才有意义IFF你的代码是不纯的和可变的:
zaz
but never actually use it inside the block. zaz
但从未在块内实际使用它。 So, the only way that this makes sense at all is if zaz
is a local variable in the outer scope and you are assigning it. zaz
是外部作用域中的局部变量,并且您正在分配它。 Although in that case, your entire loop is just equivalent to zaz = foo.last.first
. zaz = foo.last.first
。 each
evaluates the block only for its side-effects. each
仅评估其副作用。 Without side-effects, each
makes no sense at all, so the fact that you are using each
implies that you have side-effects. each
副作用就完全没有意义,因此您正在使用each
副作用这一事实意味着您有副作用。 Note that the term "immutable" without additional qualification usually refers to values. 注意,没有附加限定的术语“不变”通常是指值。 When talking about "immutable variables", we usually say "immutable variable" explicitly, to make clear that we are only talking about whether or not a variable can be re-bound, not about mutating object state.
在谈论“不可变变量”时,我们通常会明确地说“不可变变量”,以表明我们只是在谈论变量是否可以重新绑定,而不是在改变对象状态。 Or, one could just say "constant", which is the technical term for "immutable variable" … although that term already has a specific meaning in Ruby.
或者,可以只说“常量”,这是“不可变变量”的技术术语……尽管该术语在Ruby中已经具有特定的含义。
each
loops often mutate the object. each
循环通常会使对象变异。 Each has to do something. 每个人都必须做某事。 Because
each
doesn't return anything useful - it returns the array itself, It won't mutate the object if it sends every element somewhere, like to be printed on screen. 因为
each
元素都不会返回任何有用的信息-它会返回数组本身,所以如果将每个元素发送到某个地方(例如在屏幕上打印),它都不会使对象发生变异。
foo.each do |bar|
# do something with element like
# print it, change it, save it
end
Functional alterantive is map 功能替代图
foo.map { |bar| bar.something }
It returns new array which is original array processed in immutable way. 它返回新数组,这是以不变方式处理的原始数组。 Obviously you have to be careful to use immutable methods.
显然,您必须小心使用不可变的方法。 This would not be immutable:
这不是一成不变的:
foo.map { |bar| bar.something! }
Here something!
在这里
something!
does something destructive to the element of array. 对数组元素有破坏性。 However I have never seen
map
used like that. 但是我从未见过像那样使用过的
map
。 Use each
for something destructive. 使用
each
破坏性的东西。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.