Решение в исходном вопросе справедливо, как уже было сказано, замечание о том, что «my_equals» можно заменить циклом «добавить» и «поднять» другим добавлением, предоставляющим срезы исходного списка.
Однако пролог является (или это было) об искусственном интеллекте. Любой человек может ответить сразу «нет» на этот пример:
sublist([1,1,1,2], [1,1,1,1,1,1,1,1,1,1]).
, потому что человек, с простым наблюдением в списке, выводит некоторую его характеристику, как и что не существует не «2».
Вместо этого предложения действительно неэффективны в этом случае. Например, в области анализа ДНК, где изучаются длинные последовательности только четырех элементов, такие алгоритмы неприменимы.
Некоторые легкие изменения могут быть выполнены с целью взглянуть сначала на самое сильное условие. К примеру:
/* common(X, Y, C, QX, QY) => X=C+QX, Y=C+QY */
common([H|S2], [H|L2], [H|C2], DS, DL) :- !,
common(S2, L2, C2, DS, DL).
common(S, L, [], S, L).
sublist(S, L) :-
sublist([], S, L).
sublist(P, Q, L) :- /* S=P+Q */
writeln(Q),
length(P, N),
length(PD, N), /* PD is P with all unbound */
append(PD, T, L), /* L=PD+T */
common(Q, T, C, Q2, _DL), /* S=P+C+Q2; L=PD+C+_DL */
analysis(L, P, PD, C, Q2).
analysis(_L, P, P, _C, []) :- !. /* found sublist */
analysis([_|L2], P, _PD, C, []) :- !,
sublist(P, C, L2).
analysis([_|L2], P, _PD, C, Q2) :-
append(P, C, P2),
sublist(P2, Q2, L2).
Давайте попробуем это:
?- sublist([1,1,1,2], [1,1,1,1,1,1,1,1,1,1]).
[1,1,1,2]
[2]
[2]
[2]
[2]
[2]
[2]
[2]
[2]
false.
посмотреть, как "анализ" решил, что лучше искать "2".
Очевидно, что это очень упрощенное решение, в реальной ситуации лучше провести «анализ», и найденные шаблоны должны быть более гибкими (предложение ограничено шаблонами в хвосте исходного шаблона S).
'my_equals (L1, L2)' будет эквивалентно 'append (L1, _, L2)'. – lurker
Лучшее имя, чем 'my_equals', будет' prefix_of'. – repeat
@ lurker, Скажите, если я правильно вас пойму, пожалуйста. В действительности 'append (L1, _, L2)' проверяет, является ли 'L1' (целым) префикс' L2'. Аналогично, 'append (_, L1, L2)' проверяет, является ли 'L1' (целым) sufix' L2' ,. Да ? –