Я не очень разбираюсь в Visual Prolog, но постараюсь дать общий ответ. Это зависит от того, хотите ли вы найти findall/3
замену для конкретного случая или вообще.
В конкретном случае вы можете использовать аккумулятор. В вашем случае это будет список, в который добавляются значения по мере их нахождения. Что-то вроде:
acc(In, List) :-
... % do something to generate possible next value
... % test if value is already in list In
!,
Out = [Val|In], % adds to the head, but is faster than using append
acc(Out, List).
acc(List, List).
Т.е., когда вы не можете найти другое возможное значение, вы возвращаете список значений, которые вы нашли. Обратите внимание, что это может быть медленным, если вам нужно накапливать много значений, и генерация следующего возможного значения выполняется с помощью обратного отслеживания. Кроме того, это не позволит вам создавать дубликаты, поэтому это не является точной заменой findall/3
.
Если вам нужна общая замена для findall/3
, где вы можете указать цель и переменную или термин, который будет содержать экземпляр, который будет накапливаться, то вам не удастся обойти какую-то нелогическую глобальную переменную , Найдя следующее значение, вы добавляете его к тому, что было сохранено в глобальной переменной, и вызываете возврат. Если генерировать следующее значение не удается, вы извлекаете содержимое глобальной переменной и возвращаете его.