Por ejemplo, tengo variedad de hashes individualesMatriz de valores hash Hash
a = [{a: :b}, {c: :d}]
¿Cuál es la mejor manera de convertirlo en esto?
{a: :b, c: :d}
Por ejemplo, tengo variedad de hashes individualesMatriz de valores hash Hash
a = [{a: :b}, {c: :d}]
¿Cuál es la mejor manera de convertirlo en esto?
{a: :b, c: :d}
Es posible utilizar
a.reduce Hash.new, :merge
que da directamente
{:a=>:b, :c=>:d}
Tenga en cuenta que en caso de colisiones el orden es importante. hashes últimos anular asignaciones anteriores, véase, por ejemplo:
[{a: :b}, {c: :d}, {e: :f, a: :g}].reduce Hash.new, :merge # {:a=>:g, :c=>:d, :e=>:f}
Esas dos líneas son equivalentes:
total_hash = hs.reduce({}) { |acc_hash, hash| acc_hash.merge(hash) }
total_hash = hs.reduce({}, :merge)
Tenga en cuenta que Hash#merge
crea una nueva almohadilla en cada iteración, que puede ser un problema si usted está construyendo una gran hash. En ese caso, utilice update
lugar:
total_hash = hs.reduce({}, :update)
Un enfoque alternativo sería la de convertir los hashes a pares y luego construir el último hash:
total_hash = hs.flat_map(&:to_a).to_h
Puede utilizar .inject
:
a.inject(:merge)
#=> {:a=>:b, :c=>:d}
Que inicia un nuevo hash en cada iteración de los dos fusionados. Para evitar esto, puede utilizar destructiva :merge!
(o :update
, que es lo mismo):
a.inject(:merge!)
#=> {:a=>:b, :c=>:d}
probar este
a.inject({}){|acc, hash| acc.merge(hash)} #=> {:a=>:b, :c=>:d}
'Hash.new', o como amigos, como a llámalo, '{}' :-) Tanto como me gusta la solución funcional pura, ten en cuenta que 'merge' creará un nuevo hash en cada iteración; podemos usar 'update' en su lugar (no se equivocará con los hashes de entrada, ese es el punto importante):' hs.reduce ({},: update) ' – tokland
Maravillosamente hecho – Aeramor
@tokland, publique su comentario como algo separado respuesta - debería tener más visibilidad – Jason