Reputation: 13
It is interesting for me if there is any built-in tool, in Prolog, that would work for the following example:
parentRole(X,Y,Z):- parent(X,Y), male(X), !, Z=='father', !.
parentRole(X,Y,Z):- parent(X,Y), Z=='mother'.
I want the rule parent(X,Y)
to stop the program (+return false) if parent(X,Y)
failed, in rule #1, else go on as usually.
This way I'd be able to write:
parentRole(X,Y,Z):- parent(X,Y), male(X), !, Z=='father', !.
parentRole(X,Y,Z):- Z=='mother'.
Suppose facts are:
parent(myMom, i)
male(i)
I expect for the scope:
parentRole(notMyMom, i, 'mother')
the program to stop and return false, but in the real, it fails at parent(X,Y)
in the 1st rule, and tries to satisfy the 2nd, and it return true as Z=='mother'
Thanks.
Upvotes: 0
Views: 1119
Reputation: 1394
So you want
parentRole(X,Y,Z) :-
( parent(X,Y) ->
( male(X) -> Z == 'father'
; Z == 'mother' ).
; fail ).
which is the same as
parentRole(X,Y,Z) :-
parent(X,Y),
( male(X) -> Z == 'father' ; Z == 'mother' ).
Now your example fails, as expected.
Your comment: try this formatting
parentRole(X,Y,Z) :-
( parent(X,Y) ->
( male(X) ->
( Z == 'father' ->
write('father')
; fail )
; ( Z == 'mother' ->
write('mother')
; fail ) )
; fail ).
Upvotes: 1
Reputation: 11018
It makes sense to define a separate rule that verifies the gender.
parentRole(X, Y, Z) :- parent(X, Y), parentGender(X, Z).
parentGender(X, 'father') :- male(X).
parentGender(X, 'mother') :- \+ male(X).
parentRole
now only has one rule, so it will fail immediately if parent
fails.
Upvotes: 0