Это делается с использованием списка различий, и, поскольку вы изучаете, он использует спойлер AKA, представляющий собой пустые поля, на которые нужно навести курсор мыши, чтобы просмотреть содержимое. Обратите внимание, что показы не позволяют хорошее форматирование кода. В конце - финальная версия кода с хорошим форматированием, но не скрытая при открытии, поэтому не заглядывайте в видимый код в самом конце, если вы хотите попробовать его сами.
Этот ответ требует это то, что вы прочитали мою Список различий вики .
Ваша основная идея c была обоснованной, и в качестве основы для этого ответа использовался список различий. Таким образом, очевидно, большое изменение состоит в том, чтобы просто перейти от закрытого списка к открытому списку.
Поскольку ваш код рекурсивный, базовый случай можно использовать для настройки шаблона для остальных предложений предиката.
Самый простой базовый случай -
merge2([],[],[]).
но предикат, использующий список различий, может использовать различные средства для представления списка различий с использованием L-H
, которое встречается очень часто, но я его не выбрал. Вместо этого этот ответ будет следовать шаблону вики с использованием двух переменных: первой для открытого списка и второй для дыры в конце открытого списка.
Попробуйте создать простой базовый случай на вашем своя.
Далее необходимы два базовых случая, когда один из списков пуст.
Затем случаи, которые выбирают элемент из одного или другого списка.
Наконец, помощник Предикат необходим для того, чтобы можно было использовать запрос merge2(L1,L2,L3)
.
Если вы запустите код, указанный в списке, он даст многократный ответ из-за возврата. Несколько сокращений решат проблему.
merge2(L1,L2,L3) :-
merge2_prime(L1,L2,Hole0,Hole),
Hole = [],
L3 = Hole0.
merge2_prime([],[],Hole,Hole) :- !.
merge2_prime([X],[],Hole0,Hole) :-
!,
Hole0 = [X|Hole].
merge2_prime([],[Y],Hole0,Hole) :-
!,
Hole0 = [Y|Hole].
merge2_prime([X|List1],[Y|List2],Hole0,Hole) :-
X =< Y,
!,
Hole0 = [X|Hole1],
merge2_prime(List1,[Y|List2],Hole1,Hole).
merge2_prime(List1,[Y|List2],Hole0,Hole) :-
Hole0 = [Y|Hole1],
merge2_prime(List1,List2,Hole1,Hole).
Пример выполнения:
?- merge2([1,3,4],[2,5,6],L).
L = [1, 2, 3, 4, 5, 6].
?- merge2([0],[0],L).
L = [0, 0].
Я не проверял это на большом количестве примеров, так как это было просто для демонстрации того, что ответ может быть найдено с использованием списка различий.