2017-07-08 6 views
0

Was ist der beste Weg, um einen Hash in Ruby zu duplizieren und unabhängig vom Original zu haben? Zum Beispiel:Duplicate-Hash in unabhängigen Hash (flache Kopie)

a = { foo1: "bar1" } 
b = a # or b = a.clone/b = a.dup for that matter 
b[:foo2] = "bar2" 

Dies führt dazu:

{:foo1=>"bar1", :foo2=>"bar2"} # a 
{:foo1=>"bar1", :foo2=>"bar2"} # b 

Wo ich es möchte

{:foo1=>"bar1"}    # a 
{:foo1=>"bar1", :foo2=>"bar2"} # b 

Jetzt zu sein weiß ich über b = Marshal.load(Marshal.dump(a)) aber das scheint wie ein wenig übertrieben, und ich Ich frage mich, ob es einen besseren Weg gibt, weil ich es nicht wirklich finden kann.

+1

Es funktioniert für mich mit 'dup' ... –

+0

Was? Jetzt macht es auch für mich. Ich habe alles versucht und nichts schien zu funktionieren ... Was ist das für eine Zauberei? :(Danke trotzdem. –

Antwort

1

Sie könnten

a = { k: 'dog' } 
b = {}.merge(a) 
    #=> {:k=>"dog"} 
b[:cat] = 'meow' 

a #=> {:k=>"dog"} 
b #=> {:k=>"dog", :cat=>"meow"} 

aber wir vorsichtig

a = { k: [:cow, :pig] } 
b = {}.merge(a) 
    #=> {:k=>[:cow, :pig]} 
b[:k] << 'chicken' 
    #=> [:cow, :pig, "chicken"] 

a #=> {:k=>[:cow, :pig, "chicken"]} 
b #=> {:k=>[:cow, :pig, "chicken"]} 

a ist nicht schreiben, was wir wollen.

Eine Möglichkeit, erstellen Sie eine tiefe Kopie des Hash, um sicherzustellen, ist Marshal#dump und Marshal#load zu verwenden:

a = { :k=>[1, [2, [3, { :m=>[4] }]]] } 
b = Marshal.load(Marshal.dump(a)) 
    #=> {:k=>[1, [2, [3, {:m=>[4]}]]]} 

b[:k][-1][-1][-1][:m] << 5 

a #=> {:k=>[1, [2, [3, {:m=>[4]}]]]} 
b #=> {:k=>[1, [2, [3, {:m=>[4, 5]}]]]} 
1

Kernel#dup und Kernel#clone tun genau das, was Sie wollen:

a = {foo1: "bar1"} 
b = a.dup # or a.clone 

b[:foo2] = "bar2" 

p b 
# {:foo1=>"bar1", :foo2=>"bar2"} 
p a 
# {:foo1=>"bar1"} 

Wie Sie angefordert, es ist eine flache Kopie, obwohl:

a = {foo1: ["bar1"]} 
b = a.clone 

b[:foo1] << 'bar2' 
b[:foo3] = 'bar3' 

p a 
# {:foo1=>["bar1", "bar2"]} 
p b 
# {:foo1=>["bar1", "bar2"], :foo3=>"bar3"} 
Verwandte Themen