0

I Need help .I've done a small sort algorithm :

%give the max Element of a List

max([A],A):-!.
max([X|Xs],M):- max(Xs,M1), M1 > X , M is M1, !.
max([X|_],M):- M is X.

%Delete the element M from list and give back Lo

delete(_,[],[]):-!.
delete(M,[M|Lo],Lo):- !.
delete(M,[X|Xs],L1):- delete(M,Xs,Lo), L1 = [X|Lo].

%sort a list of number with no repetitions

sort([],[]):-!.
sort(L,Lo):- max(L,M), delete(M,L,L1), sort(L1,L2), Lo = [M|L2].

It DOES works, but only for 9 numbers in a list.

For example,

sort([4,5,9,1,2,44,21,10,15],Lo) does

Lo = [44, 21, 15, 10, 9, 5, 4, 2, 1].

but if i write

sort([5,4,6,7,27,2774,22,1,0,10,22,900,8],Lo).
Lo = [2774, 900, 27, 22, 22, 10, 8, 7, 6|...].

i dont understand the " |... " Is my code wrong? Doenst it support more than 9 number? is overflow?

YonCho
  • 21
  • 8
  • Oh sorry, i didnt notice. But it means i cannot use ''cut'' in sort([],[]):-!. Rigth? Otherwise, i cant press ''W'' after the result – YonCho Feb 17 '15 at 23:17
  • 1
    It has noting to do with the cuts. SWI Prolog just shortcuts displaying an entire list more than about 10 elements. If you look at the settings in the manual, it explains how you can change that behavior. There are several issues with the program, though. If you find yourself using lots of cuts, it means your logic isn't proper. And the use of `is/2` to assign means this will only work for numbers. You should use unification instead (`=/2`) then you can do, `sort([l,h,a,e,c], L).`. – lurker Feb 17 '15 at 23:23
  • I know what you mean. I can't sort letters. Im trying to change the code to letters but i fail in function max. max([A],A):-!. max([X|Xs],M):- max(Xs,M1), M1 > X , M = M1, !. max([X|_],M):- M = X. I dont figure what's wrong. – YonCho Feb 18 '15 at 01:48
  • For non-numerics, you also need to use a more general comparison operator: `@>` instead of `>`. The standard comparison operators are for numeric expressions. – lurker Feb 18 '15 at 02:04
  • Thanx again! Now i can sort letters too. Please, you said about 'using a lot of cuts' is affecting the logic and it make severals issues. I understand the 'cut' as the end of the search in backtracking and for not searching in another path after find True in a preddicate. I'd appreciate if you could explain where my logic fails or the serveral issues. Im justing learning this. – YonCho Feb 18 '15 at 02:26
  • The cut does indeed do that, but you don't really need it in most places (if any). One thing you can do is experiment by removing different cuts and see what happens. Remove the cuts from your `delete` and rewrite the last clause as, `delete(M,[X|Xs], [X|Lo]) :- X \== M, delete(M, Xs, Lo).` Remove the cut from the first `sort/2` clause: `sort([], [])`. You could use the `max_list` or `maxlist` predicate that Prolog provides, and so get rid of `max`. (NOTE: `delete`, `sort`, and `max` are often lib predicates and best avoided as user-defined predicates - name them something else). – lurker Feb 18 '15 at 13:48

0 Answers0