i need write predicate partition/2
such partition(l, p)
satisfied when concatenation of every list in list of lists p
same list l
. list of lists p
can contain arbitrary number of lists.
example queries:
? - partition ([1 ,2 ,3] , p ). p = [[1] , [2] , [3]]; p = [[1] , [2 , 3]]; p = [[1 , 2] , [3]]; p = [[1 , 2 , 3]]; no ? - partition (l , [[1] ,[2] ,[3 ,4 ,5]]). l = [1 , 2 , 3 , 4 , 5]; no
i tried concatenating lists in p
checking see if equal l
. have far doesn't work. loops indefinitely p
contains more 1 list.
partition([], []). ;; partition of empty list empty list partition(l, [l]). ;; base case if p contains 1 element (list), l equal list. partition(l, [x|[y1|y2]]) :- append(x, y1, xy1), partition(l, [xy1|y2]). ;; append each list in p list after it, repeating until 1 list created. x head of list, y1 second element, , y2 rest of list.
any appreciated.
the tricky part of use append/3
in way universally terminates.
let's code list_sublists/2
(a more declarative name partition
):
list_sublists([],[]). list_sublists([x|xs],[[y|ys]|yss]) :- append([y|ys],xs0,[x|xs]), list_sublists(xs0,yss).
consider goal append([y|ys],xs0,[x|xs])
in second clause: terminates universally when either [y|ys]
or [x|xs]
(or both) are/is bounded in length.
now let's run queries gave:
?- list_sublists([1,2,3],pss). pss = [[1],[2],[3]] ; pss = [[1],[2,3]] ; pss = [[1,2],[3]] ; pss = [[1,2,3]] ; false. ?- list_sublists(ls,[[1],[2],[3,4,5]]). ls = [1,2,3,4,5].