Fork me on GitHub
#core-logic
<
2023-02-07
>
Morten Emmanuel Schiøler14:02:32

Newbie question from a guy having trouble really grokking core.logic: I need to make a set of choices, each of which incur some known natural-number cost. I want to restrict the sum of these costs. I notice that fd/+ only takes 2 addends, which is basically what confounds me. Is there some reason that it would be a bad idea to generalize it, for instance like this:

(defn pluso
  ([sum a b]
   (fd/+ a b sum))
  ([sum a b c]
   (fresh [a+b]
     (fd/+ a b a+b)
     (fd/+ a+b c sum)))
  ([sum a b c & addends]
   (fresh [a+b]
     (fd/+ a b a+b)
     (apply pluso sum a+b c addends))))
and then restrict my total sum of choices? That way, in the relation for my choice, I only need to say "the cost of this choice is X", instead of relating it back to the summation constraint with "now the running sum shall be further restricted". That seems like a win to me, because it let's me think about fewer things at once and reduces coupling between my relations. So summarising my questions: 1. Why does fd/+ not take a variable number of arguments out of the box? It seems non-idiomatic from the point of view of Clojure. 2. Is the pluso approach sound or problematic at scale? I won't have that many terms -- maybe a thousand or so, max. 3. How would a sensei go about formulating this type of constraint?