Prolog Create a List

30,847

Solution 1

If you want to create a list of consecutive numbers from 1 to N you can use builtin predicates findall/3 and between/3 this way:

do_list(N, L):- 
  findall(Num, between(1, N, Num), L).

?- do_list(5,L).
L = [1, 2, 3, 4, 5].

SWI also has another builtin which does just that, numlist/3:

?- numlist(1,5,L).
L = [1, 2, 3, 4, 5].

Solution 2

There are three problems with your code. The first problem is that you add X1 to the list in the clause body, but you never pass the new list back towards the head of the clause. I.e., L1 is an accumulator variable, but you need a third argument that will be bound to the final list.

The second is that the second clause only matches if the input list is empty. This will never be the case, since you add X1 to the list before calling do_list/2 recursively. I.e., you don't have a recursion anchor, and the goal ?- do_list(5,L) will never return.

The third problem is that you add X1 to the list instead of X. You'd skip the largest number.

This is how it should work:

do_list(N, L) :- do_list1(N, [], L).

do_list1(0, L, L) :- !.
do_list1(N, R, L) :- N > 0, N1 is N-1, do_list1(N1, [N|R], L).
Share:
30,847
xKalelX
Author by

xKalelX

Updated on July 09, 2022

Comments

  • xKalelX
    xKalelX almost 2 years

    I have to create list of n elements for example,

    do_list(5,L1).
    

    should return,

    L1=[1,2,3,4,5].
    

    This is what I have, but it's not working.

    do_list(X,L1):- X1 is X-1, do_list(X1,[X1|L1]).
    
    do_list(0,[]).
    
  • gusbro
    gusbro about 12 years
    @mat: You're right, updated the answer to show the alternative which seems better
  • twinterer
    twinterer about 12 years
    You do have an uncanny ability to spot problems caused by implicit use of modes! I have added a test to the second clause to avoid the problem. Thanks for pointing it out.
  • false
    false about 12 years
    You fix now also do_list(-1,L). BTW, which systems do not need this !?
  • Vishnu gondlekar
    Vishnu gondlekar about 6 years
    Please use the edit link on your question to add additional information. The Post Answer button should be used only for complete answers to the question.