rails example create array ruby arrays hashmap

example - Matriz para Hash Ruby



hash.map ruby (8)

Esto es lo que estaba buscando al buscar en Google esto:

[{a: 1}, {b: 2}].reduce({}) { |h, v| h.merge v } => {:a=>1, :b=>2}

De acuerdo, este es el trato, estuve buscando en Google durante años para encontrar una solución a esto y, aunque hay muchos por ahí, parece que no hacen el trabajo que estoy buscando.

Básicamente tengo una matriz estructurada como esta

["item 1", "item 2", "item 3", "item 4"]

Quiero convertir esto en Hash para que se vea así

{ "item 1" => "item 2", "item 3" => "item 4" }

es decir, los elementos que están en los índices "pares" son las claves y los elementos en los índices "impares" son los valores.

¿Alguna idea de cómo hacer esto limpiamente? Supongo que un método de fuerza bruta sería simplemente sacar todos los índices pares en una matriz separada y luego recorrerlos para agregar los valores.


O si tiene una matriz de matrices [key, value] , puede hacer:

[[1, 2], [3, 4]].inject({}) do |r, s| r.merge!({s[0] => s[1]}) end # => { 1 => 2, 3 => 4 }


Podrías probar así, para una sola matriz

irb(main):019:0> a = ["item 1", "item 2", "item 3", "item 4"] => ["item 1", "item 2", "item 3", "item 4"] irb(main):020:0> Hash[*a] => {"item 1"=>"item 2", "item 3"=>"item 4"}

para una matriz de matriz

irb(main):022:0> a = [[1, 2], [3, 4]] => [[1, 2], [3, 4]] irb(main):023:0> Hash[*a.flatten] => {1=>2, 3=>4}



Simplemente use Hash.[] Con los valores en la matriz. Por ejemplo:

arr = [1,2,3,4] Hash[*arr] #=> gives {1 => 2, 3 => 4}


Use to_h :

a = ["item 1", "item 2", "item 3", "item 4"] h = a.to_h # => { "item 1" => "item 2", "item 3" => "item 4" }

Para la posteridad, a continuación se encuentra la respuesta para las versiones de ruby ​​<2.1.0:

a = ["item 1", "item 2", "item 3", "item 4"] h = Hash[*a] # => { "item 1" => "item 2", "item 3" => "item 4" }

Eso es. El * se llama el operador splat .

Una advertencia por @Mike Lewis (en los comentarios): "Ten mucho cuidado con esto. Ruby expande los símbolos en la pila. Si haces esto con un gran conjunto de datos, espera explotar tu pila".

Entonces, para la mayoría de los casos de uso general, este método es excelente, pero use un método diferente si desea realizar la conversión en muchos datos. Por ejemplo, @ Łukasz Niemier (también en los comentarios) ofrece este método para grandes conjuntos de datos:

h = Hash[a.each_slice(2).to_a]


Enumerator incluye Enumerable . Desde 2.1 , Enumerable también tiene un método #to_h . Por eso, podemos escribir:

a = ["item 1", "item 2", "item 3", "item 4"] a.each_slice(2).to_h # => {"item 1"=>"item 2", "item 3"=>"item 4"}

Debido a que #each_slice sin bloque nos da el Enumerator , y según la explicación anterior, podemos llamar al método #to_h en el objeto Enumerator .


a = ["item 1", "item 2", "item 3", "item 4"] Hash[ a.each_slice( 2 ).map { |e| e } ]

o, si odias Hash[ ... ] :

a.each_slice( 2 ).each_with_object Hash.new do |(k, v), h| h[k] = v end

o, si eres un fanático de la programación funcional rota:

h = a.lazy.each_slice( 2 ).tap { |a| break Hash.new { |h, k| h[k] = a.find { |e, _| e == k }[1] } } #=> {} h["item 1"] #=> "item 2" h["item 3"] #=> "item 4"