Вычесть два хэша в Ruby
может hash
класс можно изменить так, чтобы при наличии двух хэшей можно было создать новый хэш, содержащий только ключи, присутствующие в одном хэше, но не в другом?
например:
h1 = {"Cat" => 100, "Dog" => 5, "Bird" => 2, "Snake" => 10}
h2 = {"Cat" => 100, "Dog" => 5, "Bison" => 30}
h1.difference(h2) = {"Bird" => 2, "Snake" => 10}
дополнительно difference
метод может включать любые пары ключ / значение, такие что ключ присутствует в обоих хэшах, но значение отличается между ними.
4 ответов
h1 = {"Cat" => 100, "Dog" => 5, "Bird" => 2, "Snake" => 10}
h2 = {"Cat" => 999, "Dog" => 5, "Bison" => 30}
Случай 1: сохранить все пары ключ / значение k=>v
на h1
для которого нет ключа k
на h2
это один из способов:
h1.dup.delete_if { |k,_| h2.key?(k) }
#=> {"Bird"=>2, "Snake"=>10}
вот еще:
class Array
alias :spaceship :<=>
def <=>(o)
first <=> o.first
end
end
(h1.to_a - h2.to_a).to_h
#=> {"Bird"=>2, "Snake"=>10}
class Array
alias :<=> :spaceship
remove_method(:spaceship)
end
случай 2: Держите все пары ключ / значение в h1
, не h2
все, что вам нужно для этого:
(h1.to_a - h2.to_a).to_h
#=> {"Cat"=>100, "Bird"=>2, "Snake"=>10}
массив#to_h был представлен в Ruby 2.0. Для более ранних версий используйте хэш - [].
использовать reject
способ:
class Hash
def difference(other)
reject do |k,v|
other.has_key? k
end
end
end
отклонять только пары ключ / значение, если значения идентичны (согласно Малланагапредложение через комментарий к моему первоначальному ответу, который я удалил):
class Hash
def difference(other)
reject do |k,v|
other.has_key?(k) && other[k] == v
end
end
end