List 如何在Prolog中将split/3转换为split/4?
以下代码适用于List 如何在Prolog中将split/3转换为split/4?,list,split,prolog,clpfd,List,Split,Prolog,Clpfd,以下代码适用于拆分列表/3: split_list([], _, [[],[]]). split_list(T, 0, [[],T]). split_list([H|T], N, [[H|Y],Z]) :- N1 is N-1, split_list(T, N1, [Y,Z]). 例如: ?- split_list([a,s,d,f,g,h,j], 3, R). R = [[a, s, d], [f, g, h, j]] . % observed answ
拆分列表/3
:
split_list([], _, [[],[]]).
split_list(T, 0, [[],T]).
split_list([H|T], N, [[H|Y],Z]) :-
N1 is N-1,
split_list(T, N1, [Y,Z]).
例如:
?- split_list([a,s,d,f,g,h,j], 3, R).
R = [[a, s, d], [f, g, h, j]] . % observed answer
但是,我想将split_list/3
转换为split/4
:
?- split([a,s,d,f,g,h,j], 2, R1, R2).
R1 = [a,s], R2 = [d,f,g,h,j]. % expected answer
split(AsBs, N, As, Bs) :-
append(As, Bs, AsBs),
length(As, N).
我怎样才能得到我想要的答案?有什么建议吗?谢谢:)这里是对
split/4
的直接定义:
?- split([a,s,d,f,g,h,j], 2, R1, R2).
R1 = [a,s], R2 = [d,f,g,h,j]. % expected answer
split(AsBs, N, As, Bs) :-
append(As, Bs, AsBs),
length(As, N).
把上述问题概括一下如何
?- split([a,s,d,f,g,h,j], I, R1, R2).
I = 0, R1 = [], R2 = [a,s,d,f,g,h,j]
; I = 1, R1 = [a], R2 = [s,d,f,g,h,j]
; I = 2, R1 = [a,s], R2 = [d,f,g,h,j]
; I = 3, R1 = [a,s,d], R2 = [f,g,h,j]
; I = 4, R1 = [a,s,d,f], R2 = [g,h,j]
; I = 5, R1 = [a,s,d,f,g], R2 = [h,j]
; I = 6, R1 = [a,s,d,f,g,h], R2 = [j]
; I = 7, R1 = [a,s,d,f,g,h,j], R2 = [].
如果您对保留现有定义的语义感兴趣,可以通过这种方式重用它
split_list(L,N,R1,R2) :- split_list(L,N,[R1,R2]).
在这个答案中,我们使用约束来表示声明性整数算法
:- use_module(library(clpfd)).
现在,如果再看一下split\u5的代码,我们可以看到其中的代码:
%%拆分([],N,N0,Zs,Zs):-%%追加([],Zs,Zs)。
%%N#=N0,%
%%拆分([X | Xs],N,N0,Ys,[X | Zs]):-%追加([X | Xs],Ys,[X | Zs]):-
%%N1#=N0+1,%
%%N#>=N1,%
%%拆分(Xs、N、N1、Ys、Zs)。%附加(Xs、Ys、Zs)。
示例查询:
?- N = 2, split(XsYs, N, Xs, Ys).
XsYs = [_A,_B|Ys], N = 2, Xs = [_A,_B]
; false.
?- N = 2, XsYs = [a,b,c,d,e], split(XsYs, N, Xs, Ys).
XsYs = [a,b,c,d,e], N = 2, Xs = [a,b], Ys = [c,d,e]
; false.
?- XsYs = [a,s,d,f,g,h,j], split(XsYs, N, Xs, Ys).
XsYs = [a,s,d,f,g,h,j], N = 0, Xs = [] , Ys = [a,s,d,f,g,h,j]
; XsYs = [a,s,d,f,g,h,j], N = 1, Xs = [a] , Ys = [s,d,f,g,h,j]
; XsYs = [a,s,d,f,g,h,j], N = 2, Xs = [a,s] , Ys = [d,f,g,h,j]
; XsYs = [a,s,d,f,g,h,j], N = 3, Xs = [a,s,d] , Ys = [f,g,h,j]
; XsYs = [a,s,d,f,g,h,j], N = 4, Xs = [a,s,d,f] , Ys = [g,h,j]
; XsYs = [a,s,d,f,g,h,j], N = 5, Xs = [a,s,d,f,g] , Ys = [h,j]
; XsYs = [a,s,d,f,g,h,j], N = 6, Xs = [a,s,d,f,g,h] , Ys = [j]
; XsYs = [a,s,d,f,g,h,j], N = 7, Xs = [a,s,d,f,g,h,j], Ys = []
; false.
?- Xs = [a,b,c], Ys = [d,e,f], split(XsYs, N, Xs, Ys).
XsYs = [a,b,c,d,e,f], N = 3, Xs = [a,b,c], Ys = [d,e,f].
?-N=2,拆分(XsYs,N,Xs,Ys)。
XsYs=[[uA,[uB]Ys],N=2,Xs=[[uA,[uB]
; 错。
?-N=2,XsYs=[a,b,c,d,e],拆分(XsYs,N,Xs,Ys)。
XsYs=[a,b,c,d,e],N=2,Xs=[a,b],Ys=[c,d,e]
; 错。
?-XsYs=[a,s,d,f,g,h,j],拆分(XsYs,N,Xs,Ys)。
XsYs=[a,s,d,f,g,h,j],N=0,Xs=[],Ys=[a,s,d,f,g,h,j]
; XsYs=[a,s,d,f,g,h,j],N=1,Xs=[a],Ys=[s,d,f,g,h,j]
; XsYs=[a,s,d,f,g,h,j],N=2,Xs=[a,s],Ys=[d,f,g,h,j]
; XsYs=[a,s,d,f,g,h,j],N=3,Xs=[a,s,d],Ys=[f,g,h,j]
; XsYs=[a,s,d,f,g,h,j],N=4,Xs=[a,s,d,f],Ys=[g,h,j]
; XsYs=[a,s,d,f,g,h,j],N=5,Xs=[a,s,d,f,g],Ys=[h,j]
; XsYs=[a,s,d,f,g,h,j],N=6,Xs=[a,s,d,f,g,h],Ys=[j]
; XsYs=[a,s,d,f,g,h,j],N=7,Xs=[a,s,d,f,g,h,j],Ys=[]
; 错。
?-Xs=[a,b,c],Ys=[d,e,f],拆分(XsYs,N,Xs,Ys)。
XsYs=[a,b,c,d,e,f],N=3,Xs=[a,b,c],Ys=[d,e,f]。
脚注1:为了强调这些相似之处,对fd_length/2
(优化变量)的程序文本进行了轻微修改:
L
被Xs
取代,
参数对N,N0
由N,N0
和
(is)/2通过(#=)/2
。
是的,对不起,你是对的-@repeat没什么大不了的。第一个列表的长度总是正好等于N吗?是的,我想@repeat我建议把length
放在前面,因为N
很可能是给定的。@false。这样做,但为了保留有利的终止属性而使用延迟实现如何?对于简单的预期用例,您的版本会留下一个CP,并且不会因为:split(XsYs,2,Xs,Ys)
?- N = 2, split(XsYs, N, Xs, Ys).
XsYs = [_A,_B|Ys], N = 2, Xs = [_A,_B]
; false.
?- N = 2, XsYs = [a,b,c,d,e], split(XsYs, N, Xs, Ys).
XsYs = [a,b,c,d,e], N = 2, Xs = [a,b], Ys = [c,d,e]
; false.
?- XsYs = [a,s,d,f,g,h,j], split(XsYs, N, Xs, Ys).
XsYs = [a,s,d,f,g,h,j], N = 0, Xs = [] , Ys = [a,s,d,f,g,h,j]
; XsYs = [a,s,d,f,g,h,j], N = 1, Xs = [a] , Ys = [s,d,f,g,h,j]
; XsYs = [a,s,d,f,g,h,j], N = 2, Xs = [a,s] , Ys = [d,f,g,h,j]
; XsYs = [a,s,d,f,g,h,j], N = 3, Xs = [a,s,d] , Ys = [f,g,h,j]
; XsYs = [a,s,d,f,g,h,j], N = 4, Xs = [a,s,d,f] , Ys = [g,h,j]
; XsYs = [a,s,d,f,g,h,j], N = 5, Xs = [a,s,d,f,g] , Ys = [h,j]
; XsYs = [a,s,d,f,g,h,j], N = 6, Xs = [a,s,d,f,g,h] , Ys = [j]
; XsYs = [a,s,d,f,g,h,j], N = 7, Xs = [a,s,d,f,g,h,j], Ys = []
; false.
?- Xs = [a,b,c], Ys = [d,e,f], split(XsYs, N, Xs, Ys).
XsYs = [a,b,c,d,e,f], N = 3, Xs = [a,b,c], Ys = [d,e,f].