俺Prologを動かす

Lispでcall/ccが動くようになったので、昔call/ccを使ってGauche上で作った俺Prologをこっちで動かしてみた。

repl> (?- (append X Y (a b c)) (write (x = X y = Y)) (fail))
(x = () y = (a b c))
(x = (a) y = (b c))
(x = (a b) y = (c))
(x = (a b c) y = ())
#f

http://kar.s206.xrea.com/lisp/?l=prolog.scm&e=%28%3F-%20%28append%20X%20Y%20%28a%20b%20c%29%29%20%28write%20%28x%20%3D%20X%20y%20%3D%20Y%29%29%20%28fail%29%29

さすがに動作は遅いが、ちゃんと動いた。(本当に遅いので低スペックのマシンでの実行注意)
カット(!)の処理に継続を使っていたので、次にカットを使ってみる。

repl> (?- (append X Y (a b c)) ! (write (x = X y = Y)) (fail))
(x = () y = (a b c))
#f

http://kar.s206.xrea.com/lisp/?l=prolog.scm&e=%28%3F-%20%28append%20X%20Y%20%28a%20b%20c%29%29%20%21%20%28write%20%28x%20%3D%20X%20y%20%3D%20Y%29%29%20%28fail%29%29

よし、ちゃんと止まった。

Prologおぼえがき

定義にはassertを使う。

(assert (append () Y Y))
(assert (append (A . X) Y (A . Z)) :- (append X Y Z))

質問には?-を使う。

(?- (append (a b) (c d) X))

Lisp側の対処

Gauche用のソースを変更なしに動かすために、今回useを以下のように定義してごまかした。

(define-macro (use . x) #t)