Welcome! Please see the About page for a little more info on how this works.

0 votes
in core.logic by
I was trying to implement a relation similar to (map + list1 list2) -> list3
My code is:



(require '[clojure.core.logic :as l])
(require '[clojure.core.logic.fd :as fd])

(defn zip+o [x y z]
  (l/conde
    [(l/== () x) (l/== () y) (l/== () z)]
    [(l/fresh [fx rx fy ry fz rz]
              (l/conso fx rx x)
              (l/conso fy ry y)
              (l/conso fz rz z)
              (fd/in fx fy fz (fd/interval 10))
              (fd/+ fx fy fz)
              (zip+o rx ry rz))]))

(def expected-solutions
  #{{:x [0 0] :y [1 1]}
    {:x [0 1] :y [1 0]}
    {:x [1 1] :y [0 0]}
    {:x [1 0] :y [0 1]}})

(l/run* [q]
        (l/fresh [x y]
                 (l/== q {:x x :y y})
                 (zip+o x y [1 1])))

;=> ({:x (1 0), :y (0 1)}
;    {:x (0 0), :y (1 1)})



I've manage to get the expected behavior (I think...) by removing the call to onceo in clojure.core.logic/enforce-constraints


(defn enforce-constraints [x]
  (all
   (force-ans x)
   (fn [a]
     (let [constrained (enforceable-constrained a)]
       (verify-all-bound a constrained)
       ((force-ans constrained) a) ;;  <--- Here
       #_((onceo (force-ans constrained)) a)))))


Sadly it breaks one test...


FAIL in (test-simplefd-in-last) (tests.clj:1797)
expected: (= (run* [q] (fresh [x y z p0 p1] (== q [x y]) (fd/+ x y 9) (fd/* x 2 p0) (fd/* y 4 p1) (fd/+ p0 p1 24) (fd/in x y z (fd/interval 0 9)))) (quote ([6 3])))
  actual: (not (= ([6 3] [6 3] [6 3] [6 3] [6 3] [6 3] [6 3] [6 3] [6 3] [6 3]) ([6 3])))



I hope it will at least help you to find the real problem.

2 Answers

0 votes
by

Comment made by: pbaille

this test is actually a bit weird, since it introduce a fresh lvar z and give it the domain 0..9 but never use it...

0 votes
by
Reference: https://clojure.atlassian.net/browse/LOGIC-185 (reported by alex+import)
...