Отрицание определяется через отсечение
not (P) :-
P, !, fail;
true.
r(a).
g(b).
p(X) :- not r(X).
?- g(X), p(X).
X = b
Yes
?- p(X), g(X).
No
Порядок целей повлиял на работу программы. В первом случае, когда вызывается подцель p(X), переменная X уже конкретизована значением b. Во втором случае p(X) вызывается со свободной переменной.
Что касается трудностей Пролога, то подобное возникает и в других языках.