Я просто думаю функционально:
По-видимому, предикатом для использования является predsort. Это на самом деле не ISO, а из library(list)
my_cmp(X,L,R) :-
atom_length(L,Llen),atom_length(R,Rlen),
((Llen < Rlen) -> X = '>' ;
(Llen > Rlen) -> X = '<' ;
X = '=').
sort_desc_len(L,S) :- predsort(my_cmp,L,S).
В зависимости от того, как вычисляется atom_length/2
(то есть в зависимости от того, нужно ли просто получить скрытое значение length, а не пройти по строке атома), это может быть довольно быстро.
:- begin_tests(sort_desc_len).
test(empty) :- sort_desc_len([],[]).
test(nop) :- sort_desc_len([aaa,bb,c],[aaa,bb,c]).
test(reverse) :- sort_desc_len([a,bb,ccc],[ccc,bb,a]).
test(duplicates) :- sort_desc_len([a,bb,bb,ccc],[ccc,bb,a]).
test(stability) :- sort_desc_len([i,j,k],[i,j,k]).
test(random) :- sort_desc_len([a,xx,fg,hhh,jk],[hhh,xx,fg,jk,a]).
test(exercise) :- sort_desc_len([a,bcd,ef,ghij],[ghij,bcd,ef,a]).
:- end_tests(sort_desc_len).
Итак, тесты I Herd U Liek...
?- run_tests(sort_desc_len).
% PL-Unit: sort_desc_len ....
ERROR: user://4:87:
test stability: failed
ERROR: user://4:88:
test random: failed
. done
% 2 tests failed
% 5 tests passed
К сожалению, predsort/3
удаляет дубликаты. Абсолютно должно быть predsort/4
, указывающее, должны ли дубликаты исчезнуть или нет.
?- sort_desc_len([i,j,k],X).
X = [i].
?- sort_desc_len([a,xx,fg,hhh,jk],X).
X = [hhh, xx, a].
НЕУДАЧА.
Приложение
Менее шумно с использованием compare/3
, как предложено в комментарии повторить.
Н.Б. compare/3
вызов с обменом левой и правой длин.
my_cmp(X,L,R) :-
atom_length(L,Llen),
atom_length(R,Rlen),
compare(X,Rlen,Llen).
sort_desc_len(L,S) :- predsort(my_cmp,L,S).
?- run_tests(sort_desc_len).
% PL-Unit: sort_desc_len ....
ERROR: user://1:20:
test stability: failed
ERROR: user://1:21:
test random: failed
. done
% 2 tests failed
% 5 tests passed
false.
person
David Tonhofer
schedule
03.04.2020
library(yall)
и других), возвращающей -1,0,+1 для каждой пары элементов. - person David Tonhofer   schedule 03.04.2020["z","a"]
сортировать? - person false   schedule 03.04.2020