Пролог отношения и сравнения

Пусть сказал у меня эти отношения

drive(adam, van).
drive(betty, tank).
drive(adam, truck).
drive(adam, convertible).

Как мне написать условие, чтобы узнать, Адам водит три разных автомобиля?

Я попробовал это, но это не сработало.

drivethree(A):-    
  drive(A, X),
  drive(A, Y), 
  drive(A, Z),
  X = not(Y),
  X = not(Z),
  Y = not(Z).

2 ответа

Решение

Сначала вы можете захотеть понять, почему ваша программа не работает. В конце концов, это может быть не единственная программа, которая вызывает проблемы.

Выявить неверные тестовые случаи

Проблема в том, что drivethree(X) не удается, пока вы ожидаете, что это сработает. Как мы можем локализовать проблему?

Обобщите вашу программу

Одна возможность - обобщить вашу программу, удалив одну цель за другой. Если получающаяся программа все еще терпит неудачу, ошибка должна быть даже в крошечной оставшейся части! Не нужно читать все сразу.

Я добавлю * перед целями, которые будут удалены:

: - op (920, фу, *).
*_.

drivethree(А):-    
   диск (A, X),
   * диск (A, Y), 
   * диск (A, Z),
   X = нет (Y),
   * X = нет (Z),
   * Y = нет (Z).

В этой новой программе drivethree(A) все еще терпит неудачу, но использует только две цели. Так что в этих двух целях должна быть какая-то ошибка. Чтобы лучше это увидеть, попробуйте запрос:

?- drive(A, X), X = not(Z).
false.

который снова терпит неудачу. Теперь попробуем только первую цель:

?- drive(A, X).
A = adam,
X = van ;
A = betty,
X = tank ...

так X должен быть какой-то атом, но X = not(Z) требует, чтобы это была структура с функтором not/1,

Для выражения неравенства лучше всего использовать dif(X, Z) увидеть это больше. На самом деле используйте скорее:

drivethree(A):-
   dif(X, Y),
   dif(X, Z),
   dif(Y, Z),    
   drive(A, X),
   drive(A, Y), 
   drive(A, Z).

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

Монотонность

А теперь представьте, мы добавляем новые факты drive/2 в вашу программу. Что случится? Будет adam все еще будет решение? На самом деле он всегда будет решением, если мы только добавим дополнительные факты. Это свойство известно как монотонность. Добавляя дополнительные пункты, вы будете только расширять набор решений.

Просто учтите, что вы хотите описать людей, которые водят ровно три автомобиля. И просто подождите немного и подумайте, что произойдет, если мы добавим новые факты в такую ​​программу. Теперь может случиться так, что adam больше не является решением, потому что теперь он может водить четыре или более транспортных средств. Такая программа называется немонотонной. Приступая к изучению Пролога, в первый раз держитесь подальше от немонотонных программ и придерживайтесь монотонных.

Ваш код должен работать, если вы намереваетесь " по крайней мере 3 диска", после исправления:

...
X = not(Y),
X = not(Z),
...

должно быть

...
X \= Y,
X \= Z,
...

В противном случае, для более практического определения "дисков ровно 3", вы можете использовать setof/3:

drivethree(A) :- setof(V, drive(A,V), [_,_,_]).
Другие вопросы по тегам