Related
I tried to generate all the combinations of the elements in two lists.
For example, List([1,2,3],[1,2,3],L). should return L = [[1,1],[1,2],[1,3],[2,1],[2,2],[2,3],[3,1],[3,2],[3,3]]
This is the code I wrote:
matrix(L1, L2, M, Res).
matrix([], L2, [], []).
matrix([H1|T1], L2, M, [M|Res]):- matrix(T1, L2, M_temp, Res), combo(L2, H1, [], M).
combo ([], _, Acc, Acc) :- !.
combo ([H2|T2], H_tmp, Acc, M) :- combo (T2, H_tmp, Acc, M_tmp), M = [[H_tmp,H2]|M_tmp].
but the result is: L = [[[1,1],[1,2],[1,3]],[[2,1],[2,2],[2,3]],[[3,1],[3,2],[3,3]]]
because I add the list as element instead of append each list element to Res. No success of implementing the the append.
append([1,2,3],[1,2,3],L).
append_lst([], L2, L2).
append_lst([H|T], L2, Res) :- append_lst(T, L2, Acc), Res = [H|Acc].
I think my approach is wrong.
Could you help me, please?
Well, Prolog doesn't have arrays: it just has lists. But, assuming your have two lists/sets, say
[1,2,3]
[a,b,c]
and want to generate a list containing the Cartesian product of the two sets:
[
[1,a], [1,b], [1,c],
[2,a], [2,b], [2,c],
[3,a], [3,b], [3,c],
]
The simplest way is to use findall/3 and member/2:
matrix( Xs, Ys, M ) :- findall( [X,Y] , ( member(X,Xs), member(Y,Ys) ) , M ).
And if you wanted to roll your own, it's not much more difficult. You might notice that we're using a helper predicate with an additional argument that will give us back the unbound tail of the list we're building, which gets closed when we run out of Xs.
Here's the code:
pairs( [] , _ , [] ) . % Once we exhausted the Xs, we're done.
pairs( [X|Xs] , Ys , Ps ) :- % But if we have an X, then...
pair(X,Ys,Ps, P0 ), % - pair that X with every Y, and
pairs(Xs,Ys,P0) % - and recurse down
. % Easy!
pair( _ , [] , Ps , Ps ) . % Once we've exhausted the Ys, we're done
pair( X , [Y|Ys] , [X:Y|Ps] , P0 ) :- % Otherwise, construct the X:Y pair, and
pair(X,Ys,Ps,P0) % - recurse down.
. % Even easier!
I have being using prolog and have run different programs on the SWI console multiple times but this week I encountered a program where the moment I would run it on the console on my mac as ['Users/......./desktop/tiles']. The console outputs 5 errors before immediately crashing, would anyone be able to tell me why this is happening?
jack(x,y).
:- writeln(' ').
:- writeln('>>>>>>>>>> *** Put har3.jpg into the working directory, then give goals ?- d,i. to start. *** <<<<<<<< ').
:- writeln(' ').
:- writeln(' >> ... reading the COMMENTS in the PROGRAM also helps ... << ').
:- writeln(' ').
:- writeln(' ').
cl :- free(#d),free(#mypic). %clear, if I may apply a wild surmise to my own naming.
d :-nl, write('Of course you can use any picture
as long as it is called har3.jpg ... '), nl,
write('.... and you put it where Prolog can find it.
Such as the working_directory... '),nl,nl, d1.
d1 :- % d for do, I suppose.
new(#mypic,picture('R. Harmenszoon van Rijn' )),
send(#mypic, size, size(700,750)), % the default size is too small
send(#mypic,open),
new(I,image('har3.jpg')), % use (local) variable I instead of
% global #i
new(B,grbitmap(I,point(3,3),size(5,5),point(30,20))),
send(B,name(harmensz)), % A rose by any other name... but we may have to
% find the chap, so we name him.
send(#mypic,display( B, point(400,70))).
i :- i(5,7). % default intialization
i(Mx,My) :- get(#mypic,member(harmensz), Har), % i for initialize
get(Har,image,I),
get(I,size,SI),
get(SI,width,SIW),
get(SI,height,SIH),
DX is floor((SIW-0)/Mx),write(':'),write(DX),
DY is floor((SIH-0)/My),write(DY),
new(#d,device),
send(#mypic,display(#d, point(70,70))),
make_alltiles( Mx,My,SIW,SIH,DX,DY,I),
send(Har,displayed(#off)),
% comment the line above out
% if you want leave the original jpg as a hint.
new(Box,box( #d?width, #d?height )),
send(#d,display,Box),
make_circles( Box,My,Mx),
scramble( Mx,My)
.
scramble(Mx,My) :- scramble( Mx,My,33).
scramble(_,_,0).
scramble(Mx,My,Count) :-
R is random( Mx+1),L is random( Mx+1),
U is random( My+1),D is random( My+1),
rmy(R),lm(L), um(U),dm(D),
Count1 is Count-1,
scramble(Mx,My,Count1).
make_alltiles( Mx,My,SIW,SIH,DX,DY,I) :-
make_cols( Mx,My,SIW,SIH,DX,DY,I,Mx,My).
make_cols(0,_,_,_,_,_,_,_,_).
make_cols(C,My,SIW,SIH,DX,DY,I,Mx,My) :-
make_tiles( C,My,SIW,SIH,DX,DY,I,Mx,My),
C1 is C-1,
make_cols(C1,My,SIW,SIH,DX,DY,I,Mx,My).
make_tiles(_,0,_,_,_,_,_,_,_).
make_tiles(C,R,SIW,SIH,DX,DY,I,Mx,My) :-
C0 is C-1, R0 is R-1,
X is C0*DX, Y is R0*DY,
new(A,area(X,Y,DX,DY)),
get(I,clip,A,Itile),
new(Btile,grbitmap(Itile,point(C0,R0),size(Mx,My),point(DX,DY))),
send(#d,display( Btile, point(X,Y))),
make_tiles(C,R0,SIW,SIH,DX,DY,I,Mx,My).
%----------------------------------------
rmy(Row):- send(#d, for_all, tile, message(#arg1, move_r, Row)).
lm(Row):- send(#d, for_all, tile, message(#arg1, move_l, Row)).
um(Col):- send(#d, for_some, tile, message(#arg1, move_u, Col)).
dm(Col):- send(#d, for_some, tile, message(#arg1, move_d, Col)).
:- pce_begin_class( grbitmap, bitmap,"Bitmap that moves on a grid" ).
variable(grpoint, point, both, "Grid point at which Bitmap is displayed" ).
variable(grmax, size, both, "Number of grid rectangles (= grid points -1)" ).
variable(grtile, point, both, "Size of the rectangular tiles" ).
initialise(DB, I:image=image, P:grpoint=point, M:grmax=size, T:grtile=point) :->
send(DB,send_super,initialise, I), %first we initialise a plain bitmap
send(DB,grpoint,P),
send(DB,grmax,M),
send(DB,grtile,T),
send(DB,name,tile),
send(DB,recogniser,move_gesture(left)).
move_r(DB,Row) :-> get(DB,grpoint,P),get(P,y,Py), Py =\= Row.
move_r(DB,Row) :-> get(DB,grpoint,P), get(DB,grmax,M), get(DB,grtile,T),
get(M,width,Mx),get(P,x,Px),
X1 is Px+1, Px1 is X1 mod Mx, %Px -1 for move_l
send(DB,grpoint,point(Px1,Row)),
get(T,x,Tx),get(T,y,Ty),
DisPx is Px1*Tx, DisPy is Row*Ty,
send(DB,move,point(DisPx,DisPy)).
move_l(DB,Row) :-> get(DB,grpoint,P),get(P,y,Py), Py =\= Row.
move_l(DB,Row) :-> get(DB,grpoint,P), get(DB,grmax,M), get(DB,grtile,T),
get(M,width,Mx),get(P,x,Px),
X1 is Px-1+Mx, Px1 is X1 mod Mx, %Px +1 for move_r
send(DB,grpoint,point(Px1,Row)), %
get(T,x,Tx),get(T,y,Ty),
DisPx is Px1*Tx, DisPy is Row*Ty,
send(DB,move,point(DisPx,DisPy)).
move_u(DB,Col) :-> get(DB,grpoint,P),get(P,x,Px), Px =\= Col.
move_u(DB,Col) :-> get(DB,grpoint,P), get(DB,grmax,M), get(DB,grtile,T),
get(M,height,My),get(P,y,Py),
Y1 is Py-1+My, Py1 is Y1 mod My, %Py +1 for move_d
send(DB,grpoint,point(Col,Py1)),
get(T,x,Tx),get(T,y,Ty),
DisPx is Col*Tx, DisPy is Py1*Ty,
send(DB,move,point(DisPx,DisPy)).
move_d(DB,Col) :-> get(DB,grpoint,P),get(P,x,Px), Px =\= Col.
move_d(DB,Col) :-> get(DB,grpoint,P), get(DB,grmax,M), get(DB,grtile,T),
get(M,height,My),get(P,y,Py),
Y1 is Py+1, Py1 is Y1 mod My, %Py -1 for move_u
send(DB,grpoint,point(Col,Py1)),
get(T,x,Tx),get(T,y,Ty),
DisPx is Col*Tx, DisPy is Py1*Ty,
send(DB,move,point(DisPx,DisPy)).
:- pce_end_class.
:- pce_begin_class( trcircle, circle,"we design our own button" ).
variable(func,point,both, "1st: 1,2 for row,column
and 2nd: number of row or column, 0-based" ).
initialise(C, Dia:diameter=int, Fun:func=point) :->
send(C,send_super,initialise, Dia),
send(C,colour,colour(black)),
send(C,fill_pattern, colour(yellow)),
send(C,slot,func,Fun),
send(C,recogniser, click_gesture(
left,'',single,
message(#prolog, fundl, /*#receiver*/C?func?x, /*#receiver*/C?func?y))),
send(C,recogniser,click_gesture(
right,'',single,
message(#prolog, funur, #receiver ?func?x, #receiver ?func?y))).
:- pce_end_class.
fundl(1,Y) :- lm(Y). % Well, I guess one could rewrite and get rid of these
fundl(2,X) :- um(X). % four lines
funur(1,Y) :- rmy(Y).
funur(2,X) :- dm(X).
make_circles(Box,R,C) :- make_rcircles( Box,R,C),make_bcircles( Box,R,C).
make_rcircles(Box,R,C) :- make_1rcircle( R,Box,R,C).
make_1rcircle( 0,_,_,_).
make_1rcircle( N,Box,R,C) :- get(Box,area,A),
get(A,height,Ah),get(A,x,Ax),get(A,y,Ay),get(A,width,Aw),
DY=floor((Ah)/(2*R)), N0 is N-1, Y is Ay + DY + N0*DY*2,
X is (Ax)+(Aw)+8,
new(TRC,trcircle(14,point(1,N0))),
send(TRC,center,point(X,Y)),
send(#d,display,TRC),
make_1rcircle(N0,Box,R,C).
make_bcircles(Box,R,C) :- make_1bcircle( C,Box,R,C).
make_1bcircle(0,_,_,_).
make_1bcircle(N,Box,R,C) :- get(Box,area,A),
get(A,height,Ah),get(A,x,Ax),get(A,y,Ay),get(A,width,Aw),
DX=floor((Aw)/(2*C)), N0 is N-1, X is Ax + DX + N0*DX*2,
Y is (Ay)+(Ah)+8,
new(TRC,trcircle(14,point(2,N0))),
send(#d,display,TRC),
send(TRC,center,point(X,Y)),
make_1bcircle(N0,Box,R,C).
This is my script.
The errors I see are from references to undefined predicates. Add this as the first line of your file to fix those:
:- use_module(library(pce)).
After doing some Prolog in uni and doing some exercises I decided to go along somewhat further although I got to admit I don't understand recursion that well, I get the concept and idea but how to code it, is still a question for me. So that's why I was curious if anyone knows how to help tackle this problem.
The idea is given a number e.g. 45, check whether it is possible to make a list starting with 1 going n+1 into the list and if the sum of the list is the same as the given number.
So for 45, [1,2,3,4,5,6,7,8,9] would be correct.
So far I tried looking at the [sum_list/2][1] implemented in Prolog itself but that only checks whether a list is the same as the number it follows.
So given a predicate lijstSom(L,S) (dutch for listSum), given
?- lijstSom(L, 45)
L = [1,2,3,4,5,6,7,8,9];
False
My Idea was something along the line of for example if S = 45, doing steps of the numbers (increasing by 1) and subtracting it of S, if 0 is the remainder, return the list, else return false.
But for that you need counters and I find it rather hard to grasp that in recursion.
EDIT:
Steps in recursion.
Base case empty list, 0 (counter nr, that is minus S), 45 (S, the remainder)
[1], 1, 44
[1,2], 2, 42
[1,2,3], 3, 39
I'm not sure how to read the example
?- lijstSom(L, 45)
L = [1,2,3,4,5,6,7,8,9],
False
...but think of the predicate lijstSom(List, Sum) as relating certain lists of integers to their sum, as opposed to computing the sum of lists of integers. Why "certain lists"? Because we have the constraint that the integers in the list of integers must be monotonically increasing in increments of 1, starting from 1.
You can thus ask the Prolog Processor the following:
"Say something about the relationship between the first argument of lijstSom/2 and the second argument lijstSom/2 (assuming the first is a list of monotonically increasing integers, and the second an integer):
lijstSom([1,2,3], Sum)
... should return true (because yes, there is at least one solution) and give Sum = 6 (because it constructs the solution, too ... we are some corner of Construtivism here.
lijstSom(L, 6)
... should return true (because yes, there is at least one solution) and give the solution [1,2,3].
lijstSom([1,2,3], 6)
... should return true (because yes, [1,2,3] has a sum 6); no further information is needed.
lijstSom(L, S)
... should an infinite series of true and pairs of solution ("generate the solutions").
L = [1], S = 1;
L = [1,2], S = 3;
L = [1,2,3], S = 6;
...
lijstSom([1,2,3], 7)
...should return false ("fail") because 7 is not in a relation lijstSom with [1,2,3] as 7 =/= 1+2+3.
One might even want things to have Prolog Processor say something interesting about:
lijstSom([1,2,X], 6)
X = 3
or even
lijstSom([1,2,X], S)
X = 3
S = 6
In fact, lijstSom/2 as near to mathematically magical as physically possible, which is to say:
Have unrestricted access to the full table of list<->sum relationships floating somewhere in Platonic Math Space.
Be able to find the correct entry in seriously less than infinite number of steps.
And output it.
Of course we are restricted to polynomial algorithms of low exponent and finite number of dstinguishable symbols for eminently practical reasons. Sucks!
So, first define lijstSom(L,S) using an inductive definition:
lijstSom([a list with final value N],S) ... is true if ... lijstSom([a list],S-N and
lijstSom([],0) because the empty list has sum 0.
This is nice because it gives the recipe to reduce a list of arbitrary length down to a list of size 0 eventually while keeping full knowledge its sum!
Prolog is not good at working with the tail of lists, but good with working with the head, so we cheat & change our definition of lijstSom/2 to state that the list is given in reverse order:
lijstSom([3,2,1], 6)
Now some code.
#= is the "constain to be equal" operator from library(clpfd). To employ it, we need to issue use_module(library(clpfd)). command first.
lijstSom([],0).
lijstSom([K|Rest],N) :- lijstSom([Rest],T), T+K #= N.
The above follows the mathematical desiderate of lijstSom and allows the Prolog Processor to perform its computation: in the second clause, it can compute the values for a list of size A from the values of a list of size A-1, "falling down" the staircase of always decreasing list length until it reaches the terminating case of lijstSom([],0)..
But we haven't said anything about the monotonically decreasing-by-1 list.
Let's be more precise:
lijstSom([],0) :- !.
lijstSom([1],1) :- ! .
lijstSom([K,V|Rest],N) :- K #= V+1, T+K #= N, lijstSom([V|Rest],T).
Better!
(We have also added '!' to tell the Prolog Processor to not look for alternate solutions past this point, because we know more about the algorithm than it will ever do. Additionally, the 3rd line works, but only because I got it right after running the tests below and having them pass.)
If the checks fail, the Prolog Processor will says "false" - no solution for your input. This is exactly what we want.
But does it work? How far can we go in the "mathematic-ness" of this eminently physical machine?
Load library(clpfd) for constraints and use library(plunit) for unit tests:
Put this into a file x.pl that you can load with [x] alias consult('x') or reload with make on the Prolog REPL:
:- use_module(library(clpfd)).
lijstSom([],0) :-
format("Hit case ([],0)\n"),!.
lijstSom([1],1) :-
format("Hit case ([1],1)\n"),!.
lijstSom([K,V|Rest],N) :-
format("Called with K=~w, V=~w, Rest=~w, N=~w\n", [K,V,Rest,N]),
K #= V+1,
T+K #= N,
T #> 0, V #> 0, % needed to avoid infinite descent
lijstSom([V|Rest],T).
:- begin_tests(listsom).
test("0 verify") :- lijstSom([],0).
test("1 verify") :- lijstSom([1],1).
test("3 verify") :- lijstSom([2,1],3).
test("6 verify") :- lijstSom([3,2,1],6).
test("0 construct") :- lijstSom(L,0) , L = [].
test("1 construct") :- lijstSom(L,1) , L = [1].
test("3 construct") :- lijstSom(L,3) , L = [2,1].
test("6 construct") :- lijstSom(L,6) , L = [3,2,1].
test("0 sum") :- lijstSom([],S) , S = 0.
test("1 sum") :- lijstSom([1],S) , S = 1.
test("3 sum") :- lijstSom([2,1],S) , S = 3.
test("6 sum") :- lijstSom([3,2,1],S) , S = 6.
test("1 partial") :- lijstSom([X],1) , X = 1.
test("3 partial") :- lijstSom([X,1],3) , X = 2.
test("6 partial") :- lijstSom([X,2,1],6) , X = 3.
test("1 extreme partial") :- lijstSom([X],S) , X = 1, S = 1.
test("3 extreme partial") :- lijstSom([X,1],S) , X = 2, S = 3.
test("6 extreme partial") :- lijstSom([X,2,1],S) , X = 3, S = 6.
test("6 partial list") :- lijstSom([X|L],6) , X = 3, L = [2,1].
% Important to test the NOPES
test("bad list", fail) :- lijstSom([3,1],_).
test("bad sum", fail) :- lijstSom([3,2,1],5).
test("reversed list", fail) :- lijstSom([1,2,3],6).
test("infinite descent from 2", fail) :- lijstSom(_,2).
test("infinite descent from 9", fail) :- lijstSom(_,9).
:- end_tests(listsom).
Then
?- run_tests(listsom).
% PL-Unit: listsom ...................... done
% All 22 tests passed
What would Dijkstra say? Yeah, he would probably bitch about something.
I am brand new to prolog and I feel like there is a concept that I am failing to understand, which is preventing me from grasping the concept of recursion in prolog. I am trying to return S, which is the sum of the square of each digit, taken as a list from an integer that is entered by the user in a query. E.g The user enters 12345, I must return S = (1^2)+(2^2)+(3^2)+(4^2)+(5^2) = 55.
In my program below, I understand why the each segment of the calculation of S is printed multiple time as it is part of the recursive rule. However, I do not understand how I would be able to print S as the final result. I figured that I could set a variable = to the result from sos in the second rule and add it as a parameter for intToList but can't seem to figure this one out. The compiler warns that S is a singleton variable in the intToList rule.
sos([],0).
sos([H|T],S) :-
sos(T, S1),
S is (S1 + (H * H)),
write('S is: '),write(S),nl.
intToList(0,[]).
intToList(N,[H|T]) :-
N1 is floor(N/10),
H is N mod 10,
intToList(N1,T),
sos([H|T],S).
The issue with your original code is that you're trying to handle your call to sos/2 within your recursive clause for intToList/2. Break it out (and rename intToList/2 to something more meaningful):
sosDigits(Number, SoS) :-
number_digits(Number, Digits),
sos(Digits, SoS).
Here's your original sos/2 without the write, which seems to work fine:
sos([], 0).
sos([H|T], S) :-
sos(T, S1),
S is (S1 + (H * H)).
Or better, use an accumulator for tail recursion:
sos(Numbers, SoS) :-
sos(Numbers, 0, SoS).
sos([], SoS, SoS).
sos([X|Xs], A, SoS) :-
A1 is A + X*X,
sos(Xs, A1, SoS).
You can also implement sos/2 using maplist/3 and sumlist/2:
square(X, S) :- S is X * X.
sos(Numbers, SoS) :- maplist(square, Numbers, Squares), sumlist(Squares, SoS).
Your intToList/2 needs to be refactored using an accumulator to maintain correct digit order and to get rid of the call to sos/2. Renamed as explained above:
number_digits(Number, Digits) :-
number_digits(Number, [], Digits).
number_digits(Number, DigitsSoFar, [Number | DigitsSoFar]) :-
Number < 10.
number_digits(Number, DigitsSoFar, Digits) :-
Number >= 10,
NumberPrefix is Number div 10,
ThisDigit is Number mod 10,
number_digits(NumberPrefix, [ThisDigit | DigitsSoFar], Digits).
The above number_digits/2 also handles 0 correctly, so that number_digits(0, Digits) yields Digit = [0] rather than Digits = [].
You can rewrite the above implementation of number_digits/3 using the -> ; construct:
number_digits(Number, DigitsSoFar, Digits) :-
( Number < 10
-> Digits = [Number | DigitsSoFar]
; NumberPrefix is Number div 10,
ThisDigit is Number mod 10,
number_digits(NumberPrefix, [ThisDigit | DigitsSoFar], Digits)
).
Then it won't leave a choice point.
Try this:
sos([],Accumulator,Accumulator).
sos([H|T],Accumulator,Result_out) :-
Square is H * H,
Accumulator1 is Accumulator + Square,
sos(T,Accumulator1,Result_out).
int_to_list(N,R) :-
atom_chars(N,Digit_Chars),
int_to_list1(Digit_Chars,Digits),
sos(Digits,0,R).
int_to_list1([],[]).
int_to_list1([Digit_Char|Digit_Chars],[Digit|Digits]) :-
atom_number(Digit_Char,Digit),
int_to_list1(Digit_Chars,Digits).
For int_to_list I used atom_chars which is built-in e.g.
?- atom_chars(12345,R).
R = ['1', '2', '3', '4', '5'].
And then used a typical loop to convert each character to a number using atom_number e.g.
?- atom_number('2',R).
R = 2.
For sos I used an accumulator to accumulate the answer, and then once the list was empty moved the value in the accumulator to the result with
sos([],Accumulator,Accumulator).
Notice that there are to different variables for the accumulator e.g.
Accumulator1 is Accumulator + Square,
sos(T,Accumulator1,Result_out).
this is because in Prolog variables are immutable, so one can not keep assigning new values to the same variable.
Here are some example runs
?- int_to_list(1234,R).
R = 30.
?- int_to_list(12345,R).
R = 55.
?- int_to_list(123456,R).
R = 91.
If you have any questions just ask in the comments under this answer.
So let's say I'm trying to find the sum of all factors of 5 below a certain maximum number. I'm doing this recursively, because that seemed easiest. This is my code:
isFactor(X):-
Y is X mod 5,
Y = 0.
sumAll(Number, Result):-
sumAll(Number, 0, Result).
sumAll(Number, RunningTotal, Result):-
(isFactor(Number) ->
NextTotal is RunningTotal + Number;
NextTotal is RunningTotal),
NextNumber is Number - 1,
(NextNumber > 0 ->
mulSum(NextNumber, NextTotal, NextResult);
NextResult is RunningTotal),
number(NextResult) -> % this test is so that the interpreter
write(NextResult), nl; % doesn't print out a bunch of extra stuff
true. % (the internal IDs of each binding of
% NextResult maybe?) after the answer.
Now, this works (that is, it prints the correct sum), but I am slightly miffed that I can't figure out how to arrange the code so that doing
| ?- sumAll(10, X).
binds X to 10, rather than printing '10' and asserting 'yes' at the end.
My instinct is to somehow rebind Result to NextResult if NextNumber > 0 (line 13) is true, but I suspect that's just years of Python programming trying to assert themselves.
Is there a way of 'returning' the result of a goal all the way up the nested recursions here? Or am I just thinking about this all wrong?
That's awfully complicated for something simple. To sum all elements of a list that are divisible by N, all you need is this tail recursive implementation:
sum_all( Xs , N , Sum ) :-
sum_all( Xs , N , 0 , Sum )
.
sum_all( [] , _ , S , S ) .
sum_all( [X|Xs] , N , T , S ) :-
X mod N =:= 0 ,
! ,
T1 is T+X ,
sum_all(Xs,N,T1,S)
.
sum_all( [_|Xs] , N , T , S ) :-
sum_all(Xs,N,T,S)
.
The non-tail recursive implementation is a bit simpler but will blow its stack on a long list:
sum_all( [] , _ , 0 ) .
sum_all( [X|Xs] , N , S ) :-
sum(Xs,N,T) ,
( X mod N =:= 0 -> S is T+X ; S is T )
.
You could even do something like this to decompose the extraction of "interesting" values from the summing of the list:
sum_all(Xs,N,Sum) :-
findall( X , ( member(X,Xs), X mod N =:= 0 ) , L ) ,
sum(L,Sum)
.
sum(L,S) :- sum(L,0,S).
sum( [] , S ,S ) .
sum( [X|Xs] , T ,S ) :- T1 is T+X , sum(Xs,T1,S) .
Once you have that, then you can simply say:
sum_modulo_N_values( Xs , N ) :-
sum_all(Xs,N,Sum) ,
writenl( sum = Sum )
.
Invoke it something like this
sum_modulo_N_values( [1,2,5,6,7,10,11,15,31,30] , 5 ) .
And you'll get the the expected sum = 60 written to the console.
Your code seems more complex than needed, maybe such complexity hides an important fact:
in sumAll(Number, RunningTotal, Result):- Result is a singleton. Then there are little chances to get back the computed value.
I would try to get rid of number(NextResult) -> etc.. (btw you usually need parenthesis to get the expected nesting when using if/then/else - that is (C -> T ; F) ), and 'assign' instead to Result.