Prolog:重复序列

时间:2013-12-06 07:02:44

标签: prolog

我想创建一个简单的程序,通过另一个列表重复扩展列表,但是每一步都会给出一个结果。

我有类似的东西,它只运行一次:

repeat(S, R, X) :- append(S,R,X).

:- repeat([y], [x], X).
X = [y,x].

然后我尝试了这个,它永远运行:

repeat(S, R, X) :- append(S,R,X), repeat(S,R,X).

我可以通过哪些方式输出这样的程序:

:- repeat([y], [x], X).
X = [y,x];
X = [y,x,x];
X = [y,x,x,x];
x = [y,x,x,x,x];
....

我认为我需要某种基本情况?

5 个答案:

答案 0 :(得分:1)

  

但是每一步都会给出一个结果。

如您所知,Prolog可以向后前进

然后可以更好地将功能请求与另一个列表分开,复制部分已经由append / 3覆盖。最后一个使用差异列表更好地编码,很容易通过短语/ 3接口:

% service 'grammar'
enlist(L), L --> [] ; enlist(L).

产生

?- phrase(enlist([1,2]), [], L).
L = [1, 2] ;
L = [1, 2, 1, 2] ;
...

然后我们可以写

repeat(S, R, X) :-
    append(S, P, X),
    phrase(enlist(R), [], P).

我们显然得到了

?- repeat([a,b],[1,2],L).
L = [a, b, 1, 2] ;
L = [a, b, 1, 2, 1, 2] ;
...

答案 1 :(得分:1)

你可以尝试

repeat(S, R, X) :-
    S = X; append(S,R,X1), repeat(X1,R,X).

答案 2 :(得分:1)

与CapelliC的解决方案类似,使用DCG,此处仅作为轻微变体提供,不使用append并避免R = []的冗余解决方案。

rep(S, _) --> S.
rep(S, R) --> {R \= []}, rep(S, R), R.

repeat(S, R, X) :- phrase(rep(S, R), X).

这会产生:

| ?- repeat([y], [x], L).

L = [y] ? ;

L = [y,x] ? ;

L = [y,x,x] ? ;
...

| ?- repeat([a,b],[1,2],L).

L = [a,b] ? ;

L = [a,b,1,2] ? ;

L = [a,b,1,2,1,2] ?

答案 3 :(得分:1)

难道你不能这么简单吗?

repeat(Xs,Ys,Zs) :- append(Xs,Ys,Zs) .
repeat(Xs,Ys,Zs) :- append(Xs,Ys,Ts) , repeat(Ts,Ys,Zs) .

或者

repeat(Xs,Ys,Zs) :-
  append(Xs,Ys,Ts) ,
  (
    Ts=Zs
  ;
    repeat(Ts,Ys,Zs)
  ) .

答案 4 :(得分:0)

是的,你确实需要一个基本案例。如果你想回溯(按; 获得另一个答案),你至少要有一个选择。你需要能够做出最后的选择并以不同的方式选择。

基本情况是

% We append the tail to the head.
repeat(H, T, L) :- append(H, T, L).

另一种选择是

% We repeat H and T (the base case) and then append T to that.
repeat(H, T, L) :-
   repeat(H, T, L1),
   append(L1, T, L).