RubyのHashの落とし穴?
Rubyの配列とHashを使っていて個人的にハマったのでメモ。
Hashの配列を作り、それをHashで扱うときがありましたが、Array.newで初期化してから値の変更をしようとすると全てのkeyの値が変わってしまいました。
# これはダメ
temp = {}
init = {:a => 0, :b => 0}
temp[:aaa] = Array.new(2, init)
p temp
# 値を代入
temp[:aaa][0][:a] = 1
p temp
# これはOK
temp = {}
temp[:aaa] = [
{
:a => 0,
:b => 0
},
{
:a => 0,
:b => 0
}
]
p temp
# 値を代入
temp[:aaa][0][:a] = 1
p temp
結果
{:aaa=>[{:a=>0, :b=>0}, {:a=>0, :b=>0}]}
{:aaa=>[{:a=>1, :b=>0}, {:a=>1, :b=>0}]}
{:aaa=>[{:a=>0, :b=>0}, {:a=>0, :b=>0}]}
{:aaa=>[{:a=>1, :b=>0}, {:a=>0, :b=>0}]}
(追記)
原因はこれ。
http://simanman.hatenablog.com/entry/2013/06/24/200306
初期化の仕方に問題があるみたいです。
最初の初期化で別々の配列オブジェクトを定義したつもりが、実は全て同じ配列オブジェクトを参照しているらしいですね。
ちなみに
temp[:aaa] = Array.new(2, init)
ここの部分ですが、
temp[:aaa] = Array.new(2).map{Hash.new}
のように初期化しないとダメでした。
Author And Source
この問題について(RubyのHashの落とし穴?), 我々は、より多くの情報をここで見つけました https://qiita.com/tamitami/items/e6b557619cf96ed29b1b著者帰属:元の著者の情報は、元のURLに含まれています。著作権は原作者に属する。
Content is automatically searched and collected through network algorithms . If there is a violation . Please contact us . We will adjust (correct author information ,or delete content ) as soon as possible .