Clojure 为什么sorto的这种实现没有终止?

Clojure 为什么sorto的这种实现没有终止?,clojure,clojure-core.logic,minikanren,Clojure,Clojure Core.logic,Minikanren,我是逻辑编程的初学者 我试图实现如下排序关系: (索托[3 2 1][1 2 3])->s 我正在使用clojure和core.logic: 我不明白为什么在大多数情况下这不能终止 任何想法都会有帮助,谢谢 (require '[clojure.core.logic :refer :all] '[clojure.core.logic.fd :as fd]) 首先,我定义了几个小助手: 一个简单的计数关系:(counto[ab]2)->#s 减少和减少?关系等价物: (defn

我是逻辑编程的初学者

我试图实现如下排序关系:

(索托[3 2 1][1 2 3])->s

我正在使用clojure和core.logic:

我不明白为什么在大多数情况下这不能终止

任何想法都会有帮助,谢谢

(require '[clojure.core.logic :refer :all]
         '[clojure.core.logic.fd :as fd])
首先,我定义了几个小助手:

一个简单的计数关系:
(counto[ab]2)->#s

减少和减少?关系等价物:

(defne reduceo [rel acc x y]
       ([_ _ () _] (== acc y))
       ([_ _ [fx . rx] _]
         (fresh [nacc]
                (rel acc fx nacc)
                (reduceo rel nacc rx y))))

(defne everyo [g list]
       ([_ ()])
       ([_ [fl . rl]]
         (g fl)
         (everyo g rl)))
最小关系:
(mino 12 1)->s

主要关系:
(sorto[2 3 1 4][1 2 3 4])->s

下面的运行没有终止,我想了解原因

(run* [q]
      (sorto q [1 2]))
; does not terminate

(run* [q]
      (sorto [2 1] q))
; does not terminate

(run* [a b]
      (everyo #(fd/in % (fd/interval 10)) a)
      (everyo #(fd/in % (fd/interval 10)) b)
      (sorto a b))
;neither

高层次的答案是因为连接是按顺序进行的。对它们重新排序有时可能导致程序终止——但是在一般情况下,可能不存在“良好”的顺序


看看

中的第5章老实说,我认为你需要缩小问题的范围,减少需要检查的代码。更适合。谢谢你的建议,我会仔细看一下
(defn mino [x y z]
  (conde
    [(fd/<= x y) (== x z)]
    [(fd/> x y) (== y z)]))
(defne mino* [xs y]
       ([[fxs . rxs] _]
         (reduceo mino fxs rxs y)))
(defne sorto [x y]
       ([() ()])
       ([[fx . rx] [fy . ry]]
         (fresh [x* c]
                (counto rx c)
                (counto ry c)
                (mino* x fy)
                (rembero fy x x*)
                (sorto x* ry))))
(run* [q]
      (sorto q [1 2]))
; does not terminate

(run* [q]
      (sorto [2 1] q))
; does not terminate

(run* [a b]
      (everyo #(fd/in % (fd/interval 10)) a)
      (everyo #(fd/in % (fd/interval 10)) b)
      (sorto a b))
;neither