在' reduce '中使用' next '和累加器参数



有一个cop: RuboCop::Cop::Lint::NextWithoutAccumulator

有谁能解释一下这个cop是用来做什么的,它是如何以什么方式改进代码的?

是否提高了可读性和效率?

github代码。

让我们考虑文档中的示例代码:

# bad
result = (1..4).reduce(0) do |acc, i|
  next if i.odd?
  acc + i
end

如果您在控制台中尝试此操作,您将获得nil对象的NoMethodError异常。这是因为如果没有指定对象,next"返回"nil。您可以将其视为迭代器的return

对于reduce方法,它可能会导致一些意想不到的行为,因为它需要块返回的一些值。如果i是奇数,则计算next, block给出nil作为结果。在下面的迭代器中,acc等于nil,并且不能向其添加整数。在我们的示例中,第一次迭代是针对i = 1, nextacc设置为nil作为块的结果。

在某些情况下,您可以为可枚举对象获得正确的值,但通常在内部指定next的值更安全。

Bad

result = (1..4).reduce(0) do |acc, i|
  next if i.odd?
  acc + i
end
<标题>
result = (1..4).reduce(0) do |acc, i|
  next acc if i.odd?
  acc + i
end

正如@smefju所指出的,next本身隐式返回nil,并且当它作为下一次执行块的参数传入时,将导致NoMethodError

最新更新