Ruby hash.delete(:key) deleting copies and clones as well -
from understand, when set object = another, reference, have methods .dup
, .clone
create copy of object , not reference.
however, duplicating or cloning array of hashes , when delete key original hash being deleted copies! not supposed happen, wonder i'm doing wrong.
code:
or_data = {title: 'some title', tracks: [ { name: 'track one', position: 0, artist: 'orignal artist', composer: 'original composer', duration: '1:30' }, { name: 'track two', position: 1, artist: 'some other guy', composer: 'beethoven', duration: '2:10' } ] } new_hash = or_data.dup # or new_hash = or_data.clone, either way produces same result or_data[:tracks].each { |e| e.delete(:position) }
the :position
key deleted new_hash
!
this happens regardless of whether use .dup
or .clone
.
i read post says 1 should use:
new_hash = marshal.load( marshal.dump(or_data) )
this work. why? because .dup
, .clone
"shallow copies" meaning create reference :tracks
(in example) instead of copy because array of hashes contained within hash?
have @ code below:
or_data = {title: 'some title', tracks: [ { name: 'track one', position: 0, artist: 'orignal artist', composer: 'original composer', duration: '1:30' }, { name: 'track two', position: 1, artist: 'some other guy', composer: 'beethoven', duration: '2:10' } ] } new_hash = or_data.dup p "using .dup" p "-----------" p "or_data : #{or_data.object_id}" p "new_hash : #{new_hash.object_id}" p "or_data[:tracks] :#{or_data[:tracks].object_id}" p "new_hash[:tracks] : #{new_hash[:tracks].object_id}" or_data[:tracks].each { |e| e.delete(:position) } new_hash = marshal.load( marshal.dump(or_data) ) p "marshalling" p "-----------" p "or_data : #{or_data.object_id}" p "new_hash : #{new_hash.object_id}" p "or_data[:tracks] :#{or_data[:tracks].object_id}" p "new_hash[:tracks] : #{new_hash[:tracks].object_id}"
output:
"using .dup" "-----------" "or_data : 5282580" "new_hash : 5282568" "or_data[:tracks] :5282592" "new_hash[:tracks] : 5282592" "marshalling" "-----------" "or_data : 5282580" "new_hash : 5282172" "or_data[:tracks] :5282592" "new_hash[:tracks] : 5282112"
the reason position
key gets deleted when using .dup
or .clone
because tracks
key still refers same array object. after marshalling tracks
key refers entire new array object.
Comments
Post a Comment