Reputation: 938
I am currently practicing Prolog for an exam and when I studied old exams I came across a problem, where one had to define a predicate which returns the length of a list. (Example: lengthof([a,b,c,d,e,f],Length).
evaluates to Length=6.
)
My approach was the following:
lengthof([],0).
lengthof(List,LengthNew) :- lengthof([_|List],Length),LengthNew is Length-1.
But it always threw a stack overflow error. I didn't know what I could have done wrong, so I took a look into the solutions. The solution for this problem is the following:
lengthof([],0).
lengthof([_|List],LengthNew) :- lengthof(List,Length),LengthNew is Length+1.
I am now wondering why my approach did not work out. What is wrong with this one? Logically and at first look, I think, that both approaches are equivalent.
Upvotes: 1
Views: 105
Reputation: 34
lengthof([],0).
this string means that legth of empty list is zero.
lengthof([_|List],LengthNew) :-
lengthof(List,Length),LengthNew is Length+1.
in the rule you say, that no empty list has to consider as first element (_) and other elements (List). And that length of the all list is length of "List" plus one.
But in this rule:
lengthof(List,LengthNew) :-
lengthof([_|List],Length),LengthNew is Length-1.
you say that length of initial list ("List") is length of more big list minus one. It is true for any list, but it is no solution of your problem, because your code does not calculate length of initial list - instead of this you inclrease initial list endlessly.
Your first rule that process empty list desribes condition of recursion exit. So your second rule must decrease size of list, but you try increase it, so you receive "stack overflow" error.
Upvotes: 2