Пролог найдет максимальное число в списке

Вопрос: Мне нужно найти максимальное число в списке. Например goal: maxEVEN([4,10,-2,-1,23],M). M=10. Я написал следующий код: maxeven([],M). maxeven([X|R],M):- Rest is X mod 2, isRest(Rest, X, M, R). isRest(0,X,M,[List]):- X > M, maxeven(List,X). isRest(0,X,M,[List]):- X < M, maxeven(List,M). isRest(Rest,X,M,[List]):- maxeven(List,M). Он будет бросать каждый член цикла и проверять, является ли он четным, если он проверяет, является

Вопрос:

Мне нужно найти максимальное число в списке. Например

goal: maxEVEN([4,10,-2,-1,23],M). M=10.

Я написал следующий код:

maxeven([],M). maxeven([X|R],M):- Rest is X mod 2, isRest(Rest, X, M, R). isRest(0,X,M,[List]):- X > M, maxeven(List,X). isRest(0,X,M,[List]):- X < M, maxeven(List,M). isRest(Rest,X,M,[List]):- maxeven(List,M).

Он будет бросать каждый член цикла и проверять, является ли он четным, если он проверяет, является ли это создателем, чем уже присвоенное значение M. проблема заключается в том, что для первого вызова isRest предикат значение M пусто, поэтому он всегда возвращает false. Я не знаю, какое значение я могу присвоить этой переменной в первый раз, когда этот алгоритм будет работать со всеми числами.

Лучший ответ:

есть несколько простых способов: либо сначала искать первый четный, инициализировать M, либо начать с M unbound и проверить статус с помощью var/1.

Но я думаю, что у вашего кода есть другие проблемы. Это необычный синтаксис:

isRest(0,X,M,[List]):-..

[List] это список одного элемента, поэтому я не вижу, как он соответствует вашему алгоритму. Возможно, проблема возникает из-за того, что ваш код является более сложным, чем необходимо. Если предположить, что maxeven/2 может терпеть неудачу, когда нет четных чисел, может быть просто, как

maxeven([X|Xs], M) :- 0 is X mod 2, % fail if not even ( maxeven(Xs, T), T > X, !, M = T ; M = X). maxeven([_|Xs], M) :- maxeven(Xs, M).

Как это работает: когда X четный, попробуйте увидеть, если какая-либо другая четность находится в Xs, и сравните, но если нет другого даже (например, когда X является последним), храните X. В противном случае, когда X не является четным, искать хвост Xs…

Посмотрите, можете ли понять, почему требуется разрез, и играть, перемещая его в другое место, чтобы лучше понять поток контроля Prolog… Это не очень интуитивно понятно…

Если вас интересует Prolog, не забудьте изучить его библиотеку: maxeven/2 может быть таким же простым, как

maxeven(Xs, M) :- setof(X, (member(X, Xs), 0 is X mod 2), Evens), last(Evens, M). Ответ №1

Вот хвостовая рекурсивная версия:

maxeven([X|T], MaxEven) :- 0 is X mod 2, !, maxeven(T, X, MaxEven). maxeven([_|T], MaxEven) :- maxeven(T, MaxEven). maxeven([X|T], LastMax, MaxEven) :- 0 is X mod 2, !, M is max(X, LastMax), maxeven(T, M, MaxEven). maxeven([_|T], LastMax, MaxEven) :- maxeven(T, LastMax, MaxEven). maxeven([], LastMax, LastMax).

Оцените статью
Добавить комментарий