Prolog takes an inverse predicate

I have a database that looks like

hasChild(person1, person2).
hasChild(person1, person3).
hasChild(person4, person5).

This means that (for example) person1 has a child named person2.

Then I create a predicate that identifies whether the person is a parent

parent(A):- hasChild(A,_).

Determines whether a person is a parent, that is, has children

Then I try to create a predicate childless(A)that should return true if the user has no children, which is basically an inverse parent(A).

So, I have 2 questions:

a) is it possible to somehow β€œinvert” a predicate, for example, childless(A):-not(parent(A)).or by any other way around this using hasChildeither any other method?

b) parent(A)will return the truth several times if a person has several children. Is it possible to return true only once?

+4
2

1 . , , :

childless(X) :- \+ hasChild(X, _).

"true" , . "" , , , , , . , , Prolog - .:)

2 once:

parent(A) :- once(hasChild(A, _)).

cut, :

parent(A) :- hasChild(A, _), !.

: parent/1 , . :

?- parent(X).
X = person1.

, person4.

?- childless(person4).
true.

, , " " Prolog, . - . !

, ( /) - . , , ( ?), "" . , , setof/3, :

parent(Person) :- 
  setof(X, C^hasChild(X, C), People), 
  member(Person, People).

C^hasChild(X, C) Prolog, C - ; , hasChild/2, People. , ! , member/2 , :

?- parent(person4).
true.

?- parent(X).
X = person1 ;
X = person4.

? . ? . , ? , . , .:)

Prolog not/1 \+/1; , -ISO- : not(X) \+ X.:)

+5

, !

, , , , .

"" , person/1 "", childless/1. , child_of/2, male/1, female/1, spouse_husband/2 ..

, .

/, .

:

% There is no person which is neither male nor female.
:- \+ (person(X), \+ (male(X) ; female(X))).

% Nobody is male and female (at once).
:- \+ (male(X), female(X)).

% Nobody is childless and parental (at once).
:- \+ (childless(X), child_of(_,X)).

% There is no person which is neither childless nor parental.
:- \+ (person(X), \+ (childless(X) ; child_of(_,X))).

% There is no child which is not a person.
:- \+ (child_of(X,_), \+ person(X)).

% There is no parent which is not a person.
:- \+ (child_of(_,X), \+ person(X)).

% (...plus, quite likely, a lot more integrity constraints...)

... -, . parental/1 . YMMY!

+2

Source: https://habr.com/ru/post/1617338/


All Articles