为什么在Ruby中使用keep_if跳过数组中的第一个元素?

时间:2016-06-11 00:07:47

标签: arrays ruby

emp_d = Column("employee_desgination", String)

值2在数组中出现两次,但使用以下方法错误地返回它。为什么会发生这种情况,我该怎么做才能解决它?

2 个答案:

答案 0 :(得分:4)

不幸的是,这是由于keep_if的工作方式存在一些隐藏行为。为了说明这种行为,我们可以在调试果园中使用最低悬的水果,好{'{}}:

puts

这为我们提供了以下输出:

def unique(arr)
  return arr.keep_if { |x| 
    puts x, arr.join(',')
    arr.count(x) == 1
  }
end

print unique([2, 5, 5, 4, 22, 8, 2, 8])

仔细查看每当方法发现它想要保留的新值时会发生什么:它将该值存储在数组中的一个早期索引中,覆盖已存在的值。下次找到想要保留的值时,会将其放在下一个位置,依此类推。

这意味着第一次2 2,5,5,4,22,8,2,8 5 2,5,5,4,22,8,2,8 5 2,5,5,4,22,8,2,8 4 2,5,5,4,22,8,2,8 22 4,5,5,4,22,8,2,8 8 4,22,5,4,22,8,2,8 2 4,22,5,4,22,8,2,8 8 4,22,2,4,22,8,2,8 [4, 22, 2] 查看keep_if时,会看到其中的两个,因此决定跳过它。但它会看到它要保留的2,并且会覆盖第一个4 。因此,第二次看到2时,它决定保留它。

答案 1 :(得分:1)

您在迭代时更改数组。这是Matz本人的considered undefined behavior,如果你想避免像你在那里看到的奇怪行为,你应该避免这样做。

而不是keep_if方法,您应该使用此方法:

arr.select{ |x| arr.count(x) == 1 }

这不会改变阵列,但会返回一个新阵列。