【问题标题】:In ruby, is this a two dimensional array bug? [duplicate]在 ruby​​ 中,这是一个二维数组错误吗? [复制]
【发布时间】:2017-12-12 19:19:24
【问题描述】:

我有一个方法:

def test
    f = Array.new(4,Array.new(4,false))
    f.each do |array|
        p array.inspect
    end
    f[1][1] = true
    p "after setting f[1][1]"
    f.each do |array|
        p array.inspect
    end
end

这是输出:

"[false, false, false, false]"
"[false, false, false, false]"
"[false, false, false, false]"
"[false, false, false, false]"
"after setting f[1][1]"
"[false, true, false, false]"
"[false, true, false, false]"
"[false, true, false, false]"
"[false, true, false, false]"

正如您所见,第 1 列中的所有值都变为真,为什么会发生这种情况???

【问题讨论】:

  • 不,不是错误。 Array.new(4, Array.new(4,false))f 的每一行设置为来自 Array.new(4,false)same 4 元素数组。它不会执行Array.new(4,false) 4 次。所以f 是一个包含 4 个对同一个 4 元素对象的引用的数组。
  • 是的,您的代码有错误。
  • @lurker 哈哈,这真的很棘手。感谢您指出。
  • 您的示例与文档中的示例几乎完全相同,它解释了这种确切的行为。在Stack Overflow 上也被多次询问和回答。

标签: ruby


【解决方案1】:

这不是错误。 Array.new(4, Array.new(4,false)) 创建一个包含 4 个元素的数组,其中每个元素都是 相同 数组对象,由对 Array.new(4, false) 的一次调用确定。它不会执行Array.new(4,false) 4 次,对f 的每个元素执行一次。因此,您最终会得到 f 作为对同一对象的 4 个引用的数组(单个 4 元素数组,[false, false, false, false])。

如果你想要一个包含 4 个不同的 4 元素数组的数组,在 Ruby 中有很多方法可以做到这一点。一种方法是:

f = Array.new(4) { Array.new(4, false) }

这将为您的Array.new(4) 中的每个条目分别执行Array.new(4, false)

2.4.0 :002 >  f = Array.new(4) { Array.new(4, false) }
 => [[false, false, false, false], [false, false, false, false], [false, false, false, false], [false, false, false, false]]
2.4.0 :003 > f.each do |array|
2.4.0 :004 >   p array.inspect
2.4.0 :005?> end
"[false, false, false, false]"
"[false, false, false, false]"
"[false, false, false, false]"
"[false, false, false, false]"
 => [[false, false, false, false], [false, false, false, false], [false, false, false, false], [false, false, false, false]]
2.4.0 :006 > f[1][1] = true
 => true
2.4.0 :007 > p "after setting f[1][1]"
"after setting f[1][1]"
 => "after setting f[1][1]"
2.4.0 :008 > f.each do |array|
2.4.0 :009 >   p array.inspect
2.4.0 :010?> end
"[false, false, false, false]"
"[false, true, false, false]"
"[false, false, false, false]"
"[false, false, false, false]"
 => [[false, false, false, false], [false, true, false, false], [false, false, false, false], [false, false, false, false]]
2.4.0 :011 >

有关参考,请参阅Creating Arrays 的 Ruby 文档。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2018-01-16
    • 1970-01-01
    • 1970-01-01
    • 2021-12-31
    • 2011-01-04
    • 2011-11-27
    相关资源
    最近更新 更多