illness(1).
illness(2).
illness(3).
illness(4).
illness(5).
illness(none).

cure(I):- illness(I), neq(I, none).

color(red).
color(blue).
color(white).

fluent(infected(I)):- illness(I).
fluent(tcd).
fluent(bsd).
fluent(hc).
fluent(dead).
fluent(is_color(C)):- color(C).

action(inspect).
action(stain).
action(blood_sample).
action(analyze_blood).
action(medicate(X)):- cure(X).

executable(inspect, [tcd, neg(dead)]). 
executable(stain, [neg(dead)]).
executable(blood_sample, [neg(dead)]). 
executable(analyze_blood, [bsd, neg(dead)]). 
executable(medicate(X), [neg(dead)]):-
      cure(X).


causes(stain, tcd, []).

causes(medicate(J), infected(none), [infected(J)]):-
      illness(J), action(medicate(J)), neq(J, none).

causes(medicate(J), dead, [infected(I)]):-
      illness(J), action(medicate(J)), illness(I), neq(I, J).

causes(blood_sample, bsd, []). 

determines(inspect,is_color(C)):- color(C).
determines(analyze_blood, hc).
determines(analyze_blood, neg(hc)).
 

caused([is_color(blue), tcd], neg(infected(1))).
caused([is_color(blue), tcd], neg(infected(2))).
caused([is_color(blue), tcd], neg(infected(5))).

caused([is_color(red), tcd], neg(infected(5))).
caused([is_color(red), tcd], neg(infected(3))).
caused([is_color(red), tcd], neg(infected(4))).

caused([is_color(white), tcd], neg(infected(1))).
caused([is_color(white), tcd], neg(infected(2))).
caused([is_color(white), tcd], neg(infected(3))).
caused([is_color(white), tcd], neg(infected(4))).


caused([hc, bsd], neg(infected(4))).
caused([hc, bsd], neg(infected(2))).

caused([neg(hc), bsd], neg(infected(1))).
caused([neg(hc), bsd], neg(infected(3))).
caused([neg(hc), bsd], neg(infected(5))).

caused(L, F):- 
       member(F, [infected(1), infected(2), infected(3), 
                  infected(4), infected(5), infected(none)]),
       select(F, [infected(1), infected(2), infected(3), 
                  infected(4), infected(5), infected(none)],
              Q),
       neq_I(Q, L).

neq_I([],[]).

neq_I([H|L],[neg(H)|L1]):- neq_I(L,L1).

caused([neg(illness(1)), neg(illness(2))], illness(3)).
caused([neg(illness(1)), neg(illness(3))], illness(2)).
caused([neg(illness(3)), neg(illness(2))], illness(1)).

initially(neg(infected(4))).
initially(neg(infected(5))).
initially(neg(infected(none))).

initially(neg(tcd)).
initially(neg(bsd)).
initially(neg(dead)).

sgoal(infected(none)).
sgoal(neg(dead)).

