% Prolog code for the electrical environment with negation-as-failure.
% See Example 5.27 of Artificial Intelligence 3e, http://artint.info
% Copyright David L. Poole and Alan K. Mackworth, 2023
% This work is licensed under a Creative Commons
% Attribution-NonCommercial-ShareAlike 4.0 License. (CC BY-NC-SA 4.0)

% The dynamic declaration prevents undefined predicate errors.
:- dynamic lit_l1/0, lit_l2/0, light_l1/0, light_l2/0, broken_l1/0, broken_l2/0,
	   broken_cb1/0, broken_cb2/0, live_outside/0, live_l1/0, live_l2/0,
	   live_w0/0, live_w1/0, live_w2/0, live_w3/0, live_w4/0,
	   live_w5/0, live_w6/0, up_s1/0, up_s2/0, up_s3/0.

light_l1.
light_l2.
live_outside.
live_l1 :- live_w0.
live_w0 :- live_w1, up_s2.
live_w0 :- live_w2, down_s2.
live_w1 :- live_w3, up_s1.
live_w2 :- live_w3,  \+ up_s1.
live_l2 :- live_w4.
live_w4 :- live_w3, up_s3.
live_p_1 :- live_w3.
live_w3 :- live_w5, ok_cb1.
live_p_2 :- live_w6.
live_w6 :- live_w5, ok_cb2.
live_w5 :- live_outside.
lit_l1 :- light_l1, live_l1, ok_l1.
lit_l2 :- light_l2, live_l2, ok_l2.

ok_l1 :- \+ broken_l1.
ok_l2 :- \+ broken_l2.
ok_cb1 :- \+ broken_cb1.
ok_cb2 :- \+ broken_cb2.

% down is the default (if neither are specified)
down_s1 :- \+ up_s1.
down_s2 :- \+ up_s2.
down_s3 :- \+ up_s3.

up_s2.
up_s3.

% some queries:
% ?- down_s1.
% ?- down_s2.
% ?- lit_l1.
% ?- lit_l2.
