2016-04-08 4 views
1

Я не хочу, чтобы удалить [:b :B] из [[:a :A] [:b :B] [:c :C]] в следующем примере кода, и если я заменю :B с (lvar), он больше не работает:Как удалить [: b (lvar)] из [[: a: A] [: b: B] [: c: C]] в Clojure core.logic?

;; Helper Function 
(defne not-membero [x l] 
    ([_ []]) 
    ([_ [?y . ?r]] 
    (!= x ?y) 
    (not-membero x ?r))) 

Эти работы:

(run* [q] 
    (membero q [[:a :A] [:b :B] [:c :C]]) 
    (not-membero q [[:b :B]])) 
(run* [q] 
    (membero q [[:a :A] [:b :B] [:c :C]]) 
    (!= q [:b :B])) 
;; both return [[:a :A] [:c :C]], as expected 

Это не (уведомление lvar):

(run* [q] 
    (membero q [[:a :A] [:b :B] [:c :C]]) 
    (not-membero q [[:b (lvar)]])) 
(run* [q] 
    (membero q [[:a :A] [:b :B] [:c :C]]) 
    (!= q [:b (lvar)])) 
;; both return [[:a :A] [:b :B] [:c :C]], unexpected 

ответ

0

Я считаю, что причина этого не делает, t в вашем примере состоит в том, что созданный (lvar) несвязан/не связан с какой-либо другой логической переменной в программе. Ваша программа прекрасно работает (по крайней мере, я думаю, что это то, что вы хотите), если вы используете fresh логическую переменную:

(run* [q] 
    (fresh [x] 
    (membero q [[:a :A] [:b x] [:c :C]]) 
    (not-membero q [[:b x]]))) 
=> ([:a :A] [:c :C]) 
(run* [q] 
    (fresh [x] 
    (membero q [[:a :A] [:b x] [:c :C]]) 
    (!= q [:b x]))) 
=> ([:a :A] [:c :C]) 

В качестве альтернативы, они возвращают тот же результат без знания :b элемента в кортеже:

(run* [q] 
    (fresh [x] 
    (membero q [[:a :A] x [:c :C]]) 
    (not-membero q [x]))) 
(run* [q] 
    (fresh [x] 
    (membero q [[:a :A] x [:c :C]]) 
    (!= q x))) 
Смежные вопросы