2012-07-20 20 views
5

Soy nuevo en Clojure y parece que no puedo encontrar la forma de hacer algo que estoy seguro es trivial. Miré la función assoc ya que creo que esta podría ser la respuesta, pero no puedo hacer que funcione.clojure 101 combinando vectores en un mapa

lo que tengo:

keys => [:num, :name, :age] 
people => [ [1, "tim", 31] [2, "bob" 33] [3, "joe", 44] ] 

Lo que quiero hacer es crear un vector de mapas, cada mapa se parece a

[ { :num 1, :name "tim", :age 31 } 
    { :num 2, :name "bob", :age 33 } 
    { :num 3, :name "joe", :age 44 } ] 

Mi cerebro OO me quiere escribir un montón de bucles, pero sé que hay una mejor manera en la que estoy perdido en la gran API.

+1

"Mi cerebro OO quiere que escriba un montón de bucles" << Los bucles son una característica de la programación imperativa, no OOP. Los dos son ortogonales. – missingfaktor

Respuesta

10

Prueba esto:

(def ks [:num :name :age]) 
(def people [[1 "tim" 31] [2 "bob" 33] [3 "joe" 44]]) 

(map #(zipmap ks %) people) 

=> ({:num 1, :name "tim", :age 31} 
    {:num 2, :name "bob", :age 33} 
    {:num 3, :name "joe", :age 44}) 

cuenta que he utilizado en lugar de kskeys para dar nombre a las teclas, como keys es un procedimiento integrado en Clojure y que es una mala idea para redefinirlo. También tenga en cuenta que map devuelve una secuencia floja; Si es absolutamente necesario un vector, a continuación, hacer esto:

(vec (map #(zipmap ks %) people)) 

=> [{:num 1, :name "tim", :age 31} 
    {:num 2, :name "bob", :age 33} 
    {:num 3, :name "joe", :age 44}] 
+1

¡Sí! Eso es exactamente lo que estaba buscando y estaba bailando por un tiempo. ¡Gracias! – rooftop

+0

¡Es un placer! :) –

1

Un poco poco más elegante, usando clojure.core/partial:

(map (partial zipmap keys) people) 

Y como sugirió Óscar, se debe utilizar un nombre diferente para su keys.

+0

Usa 'mapv' para que coincida con lo que Óscar está pidiendo. – sortega