Skip to content

Instantly share code, notes, and snippets.

@urbanautomaton
Last active September 11, 2018 20:24
Show Gist options
  • Save urbanautomaton/069af8e6556b717288edcf54a36f631b to your computer and use it in GitHub Desktop.
Save urbanautomaton/069af8e6556b717288edcf54a36f631b to your computer and use it in GitHub Desktop.
% vim: set ft=prolog:
color(red).
color(green).
color(yellow).
color(blue).
color(white).
nat(brit).
nat(dane).
nat(swede).
nat(norwegian).
nat(german).
drink(tea).
drink(coffee).
drink(milk).
drink(beer).
drink(water).
cigar(pallmall).
cigar(dunhill).
cigar(blends).
cigar(bluemaster).
cigar(prince).
pet(dogs).
pet(birds).
pet(horses).
pet(cats).
pet(fish).
colors(Cs) :- findall(C, color(C), Cs).
nats(Ns) :- findall(N, nat(N), Ns).
drinks(Ds) :- findall(D, drink(D), Ds).
cigars(Cs) :- findall(C, cigar(C), Cs).
pets(Ps) :- findall(P, pet(P), Ps).
valid_street(Street) :-
colors(Colors),
nats(Nats),
drinks(Drinks),
cigars(Cigars),
pets(Pets),
valid_street_(Colors, Nats, Drinks, Cigars, Pets, Street).
valid_street_([], [], [], [], [], []).
valid_street_(Colors, Nats, Drinks, Cigars, Pets, [(Color, Nat, Drink, Cigar, Pet)|T]) :-
select(Color, Colors, ColorsRest),
select(Nat, Nats, NatsRest),
select(Drink, Drinks, DrinksRest),
select(Cigar, Cigars, CigarsRest),
select(Pet, Pets, PetsRest),
valid_street_(ColorsRest, NatsRest, DrinksRest, CigarsRest, PetsRest, T).
neighbour(H1, H2, Houses) :-
pair_in(Houses, [H1, H2]) ; pair_in(Houses, [H2, H1]).
pair_in([H1,H2|_], [H1, H2]).
pair_in([_,H|T], P) :- pair_in([H|T], P).
% (color, nat, drink, cigar, pet)
street(Houses) :-
Houses = [
(_, _, _, _, _),
(_, _, _, _, _),
(_, _, _, _, _),
(_, _, _, _, _),
(_, _, _, _, _)
],
member((red, brit, _, _, _), Houses), % the Brit lives in the red house
member((_, swede, _, _, dogs), Houses), % the Swede keeps dogs as pets
member((_, dane, tea, _, _), Houses), % the Dane drinks tea
member((green, _, coffee, _, _), Houses), % the green house's owner drinks coffee
member((_, _, _, pallmall, birds), Houses), % the person who smokes Pall Mall rears birds
member((yellow, _, _, dunhill, _), Houses), % the owner of the yellow house smokes Dunhill
Houses = [_, _, (_, _, milk, _, _), _, _], % the man living in the center house drinks milk
Houses = [(_, norwegian, _, _, _) | _], % the Norwegian lives in the first house
member((_, _, beer, bluemaster, _), Houses), % the owner who smokes BlueMaster drinks beer
member((_, german, _, prince, _), Houses), % the German smokes Prince
pair_in(Houses, [(green, _, _, _, _), (white, _, _, _, _)]), % the green house is on the left of the white house
neighbour((_, norwegian, _, _, _), (blue, _, _, _, _), Houses), % the Norwegian lives next to the blue house
neighbour((_, _, _, blends, _), (_, _, _, _, cats), Houses), % the man who smokes blends lives next to the one who keeps cats
neighbour((_, _, _, _, horses), (_, _, _, dunhill, _), Houses), % the man who keeps horses lives next to the man who smokes Dunhill
neighbour((_, _, _, blends, _), (_, _, water, _, _), Houses), % the man who smokes blend has a neighbor who drinks water
valid_street(Houses).
% ?- [einstein].
% true.
%
% ?- street(H).
% H = [(yellow, norwegian, water, dunhill, cats), (blue, dane, tea, blends,
% horses), (red, brit, milk, pallmall, birds), (green, german, coffee,
% prince, fish), (white, swede, beer, bluemaster, dogs)] ;
% false.
% Example query for "which is the green house":
%
% ?- street(H), nth0(N, H, (green, _, _, _, _)).
% H = [(yellow, norwegian, water, dunhill, cats), (blue, dane, tea, blends,
% horses), (red, brit, milk, pallmall, birds), (green, german, coffee,
% prince, fish), (white, swede, beer, bluemaster, dogs)],
% N = 3 ;
% false.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment