Rubyで2次元配列

size = 3
a = Array.new(size){
     Array.new(size, 0)
}


とするのが正解。
こうすると

pp a
a[1][2] = 1
pp a

と出力したときに

[[0, 0, 0]
 [0, 0, 0]
 [0, 0, 0]]

[[0, 0, 0]
 [0, 0, 1]
 [0, 0, 0]]

と出力してくれる。
これは配列の各列を初期化するときに、毎回ブロックを呼んでくれるため。


ひっかかるところは

size = 3
a = Array.new(size, Array.new(size, 0))


こう作ったときに上と同じ様になるような気がするが、実際は、

a[1][1] = 1
pp a
[[0, 1, 0]
 [0, 1, 0]
 [0, 1, 0]]

となってしまいます。

この原因はa[1][2]と書いた時の、a[1]の部分が、a[0]とa[2]と全く同じ物を参照しているからです。
図にしてみました。
f:id:ryufloat:20130408213650p:plain
こうなっていたものを
f:id:ryufloat:20130408213652p:plain
このように変更してしまっているため、各列の2番目の要素がすべて変更されてしまっています。