Nubkadiya
Nubkadiya

Reputation: 3465

How to stop repetitions in rules in prolog

In my prolog rule

marriedcouple(X,Y) :-
    parent( (X,Z), bornin(_) ),
    parent( (Y,Z), bornin(_) ),
    female(X),
    male(Y)
    ;
    male(X),
    female(Y),
    different(X,Y).

when a parent has two kids, the couple shows twice. How can we prevent this ?

Upvotes: 2

Views: 2866

Answers (2)

Enigmativity
Enigmativity

Reputation: 117010

Given that you've got female/1 & male/1 predicates the predicate becomes quite simple.

marriedcouple(X,Y) :-
    parent( (X,Z), bornin(_) ),
    parent( (Y,Z), bornin(_) ),
    female(X),
    male(Y).

However, if you want to see if X and Y are not the same use the (\==)/2 operator for "not identical" or (\=)/2 for "not unifiable".


Pradeep, based on your comment below, here is a more complete solution.

In order to prevent the same answer coming back twice there's a number of choices. We can build a list of solutions and only add a newly found solution if it isn't already in the list. Or use an approach that incorporates state using the assert/1 predicate.

I've chosen the latter.

?- solve.

solve :-
    marriedcouple(Dad, Mum),
    not( found( marriedcouple(Dad, Mum) ) ),
    assert( found( marriedcouple(Dad, Mum) ) ),
    write( [Dad, Mum] ),
    nl,
    fail.

marriedcouple(Dad, Mum) :-
    parent(Dad, Child),
    parent(Mum, Child),
    male(Dad),
    female(Mum).

male(aaron).
male(adam).

female(betty).
female(eve).

parent(aaron, callum).
parent(aaron, david).
parent(adam, abel).
parent(adam, cain).
parent(betty, callum).
parent(betty, david).
parent(eve, abel).
parent(eve, cain).

When I run this I get the following:

[aaron,betty];
[adam,eve];
No.

Be careful using assert/1 predicates as you may introduce unwanted side-effects into your programs. You may need to do appropriate retract/1 calls too.

Upvotes: 2

ony
ony

Reputation: 13223

Just an theoretical solution through double-not:

marriedcouple(Dad, Mum) :-
    male(Dad), female(Mum),
    not(notMarriedcouple(Dad,Mum)).

notMarriedcouple(Dad, Mum) :-
    male(Dad), female(Mum),
    not((parent(Dad, Child), parent(Mum, Child))).

Upvotes: 1

Related Questions