1

So I've been trying to teach myself clojure and core.logic and decided to try and implement a solution to the sum product problem (http://en.wikipedia.org/wiki/Impossible_Puzzle).

So far I've implemented the first two steps.

(ns sum-product-problem.core
  (:refer-clojure :exclude [==])
  (:use clojure.core.logic)
  (:require [clojure.core.logic.fd :as fd]))

(def non-unique-factors
  (tabled [product]
    (fresh [p q x y]
      (fd/in p q x y (fd/interval 2 99))
      (fd/>= q p)
      (fd/* p q product)
      (fd/>= y x)
      (fd/* x y product)
      (fd/distinct [p x]))))

(defn inscruitable-summands [sum x]
  (fresh [y product]
    (conde
      [(fd/> (* 2 x) sum)]
      [(fd/in y (fd/interval 2 99))
       (fd/+ x y sum)
       (fd/* x y product)
       (non-unique-factors product)
       (inscruitable-summands sum (+ x 1))])))

(defn solution []
  (run* [q]
    (fd/in q (fd/interval 17 17))
    (inscruitable-summands q 2)))

This seems to give the correct answer when the domain is limited to a single number in (solution) but if I extend that domain it immediately stops working.

The results when searching over a single member domain also contains the answer multiple times. It seems to be caused by each recursion of inscruitable-summands but I'm not really sure why.

Finally, I was hoping someone could take a quick look at my non-unique-factors function. It feels like a bit of a bodge and I was wondering if anyone could suggest a better alternative?

Thanks for the help, Dean

dnolen
  • 18,496
  • 4
  • 62
  • 71

1 Answers1

0

I don't believe this puzzle is solvable with CLP(FD) facilities alone (though someone better versed in Prolog may be able to answer this one), solutions I've seen in Prolog require some form of subquery facility like like setof.

dnolen
  • 18,496
  • 4
  • 62
  • 71