Ruby数组赋值产生了意外的结果

Ruby数组赋值产生了意外的结果,ruby,Ruby,我有: 似乎是正确的 a = [['-', '-', '-'], ['-', '-', '-'], ['-', '-', '-']] b = [['-'] * 3] * 3 # => [["-", "-", "-"], ["-", "-", "-"], ["-", "-", "-"]] a == b #=> true 什么?为什么b[0][0]=“X”会在三个位置更改值 我还发现它不能这样工作: a[0][0] = 'X' a # => [["X", "-", "-"], [

我有:

似乎是正确的

a = [['-', '-', '-'], ['-', '-', '-'], ['-', '-', '-']]
b = [['-'] * 3] * 3 # => [["-", "-", "-"], ["-", "-", "-"], ["-", "-", "-"]]
a == b #=> true
什么?为什么
b[0][0]=“X”
会在三个位置更改值

我还发现它不能这样工作:

a[0][0] = 'X'
a # => [["X", "-", "-"], ["-", "-", "-"], ["-", "-", "-"]]

b[0][0] = 'X'
b # => [["X", "-", "-"], ["X", "-", "-"], ["X", "-", "-"]]

a == b # => false
b = [%w[- - -]] * 3 # => [["-", "-", "-"], ["-", "-", "-"], ["-", "-", "-"]]
b[0][0] = 'X'
b # => [["X", "-", "-"], ["X", "-", "-"], ["X", "-", "-"]]

我发现必须这样做:

a[0][0] = 'X'
a # => [["X", "-", "-"], ["-", "-", "-"], ["-", "-", "-"]]

b[0][0] = 'X'
b # => [["X", "-", "-"], ["X", "-", "-"], ["X", "-", "-"]]

a == b # => false
b = [%w[- - -]] * 3 # => [["-", "-", "-"], ["-", "-", "-"], ["-", "-", "-"]]
b[0][0] = 'X'
b # => [["X", "-", "-"], ["X", "-", "-"], ["X", "-", "-"]]
这:

将创建一个数组,其中包含对同一对象的3个引用,因此更改其中一个引用将更改所有引用,如下所示:

[object]*3
如果要使用3个不同的对象创建长度为3的数组,请执行以下操作:

a = [[1]]*3 #=> [[1], [1], [1]]
a[0][0] = 2 #=> [[2], [2], [2]]

第一次初始化创建了嵌套在1中的3个数组

a = 3.times.map {[1]} #=> [[1], [1], [1]]
a[0][0] = 2           #=> [[2], [1], [1]]
第二次初始化创建了1个数组,然后指向同一数组3次

a = [['-', '-', '-'], ['-', '-', '-'], ['-', '-', '-']]
#   [['-', '-', '-'], ['-', '-', '-'], ['-', '-', '-']] 
#         ARRAY a          ARRAY b          ARRAY c
如果您这样想,如果您更改b[0][0],则只会更改一个数组,但是您可能会有这样的印象,即更改了更多数组,因为它被引用了很多次

你可以自己检查,打印他们的地址

b = [['-'] * 3] * 3
#   [['-', '-', '-'], ['-', '-', '-'], ['-', '-', '-']] 
#         ARRAY x          ARRAY x          ARRAY x

[['-']*3]*3
创建一个数组,然后创建对同一数组对象的两个引用。但是
Array.new(3){…}
调用它的块3次,每次都创建并产生一个新对象。当出现类似这样的神秘情况时,请检查
a.map(&:object\u id)
以查看数组中有哪些对象。如果数字都是相同的,那么它们都是相同的对象。当然Ruby是正确的,除非你遇到了错误。这里没有与您所展示的内容相关的Ruby bug。您所说的“不工作”是什么意思?