2013-01-04 6 views
5

Ich versuche, Daten aus einer Karte mit Clojure core.logic zu ziehen. Dieser Code funktioniert, wie ich will es an:Extrahieren von Elementen einer Karte aus Clojure core.logic

(run 10 [q] 
    (fresh [?id ?type ?name] 
     (membero ?type [:t2 :t1]) 
     (== q [?id ?name]) 
     (membero {:id ?id :type ?type :name ?name} 
      [ 
      {:id 1 :type :t1 :name "one"} 
      {:id 2 :type :t2 :name "two"} 
      ]))) 
=> ([2 "two"] [1 "one"]) 

Allerdings, wenn ich einige andere Elemente auf der Karte hinzufügen, dann scheitert es zum Spiel:

(run 10 [q] 
    (fresh [?id ?type ?name] 
     (membero ?type [:t2 :t1]) 
     (== q [?id ?name]) 
     (membero {:id ?id :type ?type :name ?name} 
      [ 
      {:id 1 :type :t1 :name "one" :other1 :o1} 
      {:id 2 :type :t2 :name "two" :other2 :o2} 
      ]))) 

Ich verstehe, warum matcho nicht als den Karten arbeiten nicht länger gleich. Meine Frage ist, wie kann ich das ändern, damit es wieder funktioniert? Wie kann ich erreichen, dass nur einige der Schlüssel in einer Karte übereinstimmen oder wie kann ich herausfinden, welche zufälligen Schlüssel eine Karte hat?

EDIT:

ich es an die Arbeit mit patial-map (dank https://github.com/clojure/core.logic/pull/10)

(run 10 [q] 
    (fresh [?id ?type ?name] 
      (membero ?type [:t2 :t1]) 
      (== q [?id ?name]) 
      (membero (partial-map {:id ?id :type ?type :name ?name}) 
        [ 
        {:id 1 :type :t1 :name "one" :other1 :o2} 
        {:id 2 :type :t2 :name "two" :other2 :o1} 
        ]))) 

Allerdings fand ich eine Notiz, dass featurec sollte statt partial-map verwendet werden. Meine neue Frage: Wie ändere ich das um featurec zu verwenden?

+0

Ich fügte einen Gist des Testcodes hinzu, den ich verwendete: https://gist.github.com/4454548 –

Antwort

6

meine eigene Frage zu beantworten:

Hier ist der Arbeitscode:

(run 10 [q] 
    (fresh [?id ?type ?name ?pm] 
      (membero ?type [:t2 :t1]) 
      (== q [?id ?name]) 
      (featurec ?pm {:id ?id :type ?type :name ?name}) 
      (membero ?pm 
        [ 
        {:id 1 :type :t1 :name "one" :other1 :o2} 
        {:id 2 :type :t2 :name "two" :other2 :o1 :another :ao2} 
        {:id 3 :type :t3 :name "three" :other2 :o1 :another :ao1} 
        ])))) 

Dieser Code ermöglicht es mir, Werte von einer Karte zu extrahieren, sondern nur die Aufmerksamkeit auf die Tasten zu bezahlen, die wirklich wichtig sind. Der Rest der Schlüsselwertpaare wird ignoriert.