I'm trying to compare and find the difference between two nested hashes with multiple hash arrays within arrays.
What is the best way to go about this comparison? It appears there are no libraries or functions that can help with this..
For example, I want the below two examples of hash a and hash b to be considered equal.
pry(main)> a
#⇒ {"197315"=>{:qty=>1,
# :modifiers=>[{"197323-197319"=>{:qty=>1}},
# {"197322-197321"=>{:qty=>1}}]}}
pry(main)> b
#⇒ {"197315"=>{:qty=>1,
# :modifiers=>[{"197322-197321"=>{:qty=>1}},
# {"197323-197319"=>{:qty=>1}}]}}
pry(main)> a == b
#⇒ false
pry(main)> a
#⇒ {"197315"=>{:qty=>1,
# :modifiers=>[{"197322-197321"=>{
# :qty=>1,
# :modifiers=>['2222'=>'33333', '4444'=>'55555']}},
# {"197323-197319"=>{:qty=>1}}]}}
pry(main)> b
#⇒ {"197315"=>{:qty=>1,
# :modifiers=>[{"197322-197321"=>{
# :qty=>1,
# :modifiers=>['4444'=>'55555', '2222'=>'33333']}},
# {"197323-197319"=>{:qty=>1}}]}}
pry(main)> a == b
#⇒ false
This recursive solution should work with any number of levels of nested arrays and hashes.
Code
require 'set'
def arr_to_set(o)
case o
when Hash
o.each_with_object({}) { |(k,v),g| g[k] = arr_to_set(v) }
when Array
o.map { |e| arr_to_set(e) }.to_set
else
o
end
end
Examples
Example 1
a = {"197315"=>{:qty=>1, :modifiers=>[
{"197323-197319"=>{:qty=>1}},
{"197322-197321"=>{:qty=>1}}
]
}
}
b = {"197315"=>{:qty=>1, :modifiers=>[
{"197322-197321"=>{:qty=>1}},
{"197323-197319"=>{:qty=>1}}
]
}
}
arr_to_set(a) == arr_to_set(b)
#=> true
Example 2
c = {"197315"=>{:qty=>1,
:modifiers=>[
{"197322-197321"=>{ :qty=>1,
:modifiers=>['2222'=>'33333', '4444'=>'55555']
}
},
{"197323-197319"=>{:qty=>1}
}
]
}
}
d = {"197315"=>{:qty=>1,
:modifiers=>[
{"197322-197321"=>{:qty=>1,
:modifiers=>['4444'=>'55555', '2222'=>'33333']
}
},
{"197323-197319"=>{:qty=>1}
}
]
}
}
arr_to_set(c) == arr_to_set(d)
#=> true
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.