2

I need to define a predicate toAdd/3 such that if Xss and Yss are lists of lists then toAdd(X,Xss,Yss) holds if Yss can be obtained by adding the element X to the end of every element in Xss, e.g.

?- toAdd(g, [[e],[b,c,f],[k,h]], Yss).
Yss = [[e,g],[b,c,f,g],[k,h,g]].         % expected result

I know how to add an element to a list but lists of lists confuse me.

I wrote this code that adds to the end of one list, but not sublists.

add(X,[],[X]).
add(X,[A|L],[A|L1]) :-
   add(X,L,L1).
repeat
  • 18,496
  • 4
  • 54
  • 166
  • Are you still wondering where `A` comes from in your `add(X,[A|L],[A|L1])` from your comment in your first post of this problem? http://stackoverflow.com/questions/22702864/adding-an-element-to-a-list-within-a-list – lurker Mar 28 '14 at 11:41

2 Answers2

2

Let's put the predicate add/3 to use with maplist/3!

toAdd(X,Xss,Yss) :-
   maplist(add(X),Xss,Yss).

Sample query:

?- toAdd(g, [[e],[b,c,f],[k,h]], Yss).
  Yss = [[e,g],[b,c,f,g],[k,h,g]]
; false.
Community
  • 1
  • 1
repeat
  • 18,496
  • 4
  • 54
  • 166
1

split the problem in two parts:

- transform each element
  - append to tail

then

add(_,[],[]). % done
add(X,[E|Es],[T|Ts]) :-
  append(E,[X],T),
  add(X,Es,Ts).

we can do inline using findall/3 and member/2

1 ?- [user].
|: tooAdd(X, Es, Ts) :- findall(T, (member(E,Es),append(E,[X],T)), Ts).
% user://1 compiled 71.19 sec, 2 clauses
true.

2 ?- tooAdd(g, [[e], [b, c, f], [k, h]], Yss).
Yss = [[e, g], [b, c, f, g], [k, h, g]].
CapelliC
  • 59,646
  • 5
  • 47
  • 90