Learning Prolog: Lab Session #3
I'm back with the third post in this (rather unexpected) series! I think I might be getting the hang of this. It's rather abstract and difficult to visualise though. Perhaps there's a tool out there that lets you visualise your Prolog programs to better understand them (If you know of one, please leave a comment down below!) This week's lab introduced the idea of rules. A rule in Prolog is basically if this then at. For example, if the temperature is low and there are lots of clouds in the sky, the weather can be considered bad.
Here's an example:
weather(bad) :-
temperature(low),
cloud(high),
visibility(low).
weather(good) :-
temperature(high),
cloud(low),
visibility(high).
weather(unsure).
temperature(low).
cloud(high).
visibility(low).
The last 3 lines of the above describe the weather at the moment - feel free to change them. The :-
bit is simply the equivalent of the IF syntax in Prolog (rather odd if you ask me). Anyway, using the above we can now ask Prolog what the weather is like so:
?- weather(What).
What = bad .
Note that you nad to press enter in order to tell Prolog that it got the correct answer. This is because it has detected that there are other possible answers that it hasn't evaluated yet. You can press space to tell Prolog that it hasn't found the correct answer, but more on this later.
The above, in english, says something like this:
The weather is bad if the temperature is low, there's lots of cloud cover and visibility is low. The weather is good if the temperature is high, there aren't many clouds about and visibility is high. If the weather is neither of the above, then we are unsure about whether the weather good or bad.
We can also use rules in Prolog to categorise something based on a set of rules. Here's an example that works out what category a test score would fall into.
grade(distinction, Mark) :-
Mark >= 70.
grade(pass, Mark) :-
Mark >= 40,
Mark < 70.
grade(fail, Mark) :-
Mark < 40.
Using the above, we can ask Prolog questions like this:
What grade would I get if I got a mark of 86?
What grade would a mark of 52 be?
And so on. Here's how you would ask Prolog the above questions:
?- grade(Category, 87).
Category = distinction .
?- grade(Category, 52).
Category = pass .
?- grade(Category, 11).
Category = fail.
verything was all going rather well, until I got to the final excersize. It was based on getting Prolog to tell you whether a car fault was electrical or not. Here's a description of what we were asked to do:
A car fault is electrical if the car won't start or the lights are broken. A car fault is also electrical if the car won't start and the lights won't work, or the battery is flat.
After some thought, I came up with the following:
car_fault(electrical) :- % colon-if represents IF in Prolog.
wont_start; % Semi-colons represent OR in Prolog.
lights_broken. % Full stops terminate rules.
car_fault(electrical) :-
(wont_start, % Commas represent AND in Prolog.
lights_broken);
flat_battery.
wont_start.
lights_broken.
Where you define any combination of wont_start.
, lights_broken.
or flat_battery
beneath the rules, depending in your situation. However, I got a nasty error when I tried to run it, complaining that I hadn't defined something. After sone looking into it (and some help from my lecturer), we found that you need to explicitly tell Prolog that it's OK if lights_broken.
, wont_start.
, or flat_battery.
aren't defined, and that it shouldn't throw an error. You can do this like so:
:- dynamic wont_start/0.
:- dynamic flat_battery/0.
:- dynamic lights_broken/0.
Then you can ask Prolog whether your car has an electrical fault like so:
?- car_fault(What).
What = electrical .
...and Prolog will reply that yes, it is an electrical fault if the above rules are met. Otherwise, it will reply false
. To practice, try extending the above to include the following:
A car fault is mechanical if the windows have been smashed.
A car fault is also mechanical if the engine is smoking, or if the engine is making a loud noise.
Just ask in the comments for the answer to the above, or if you need help. Also note that I can't tell who's reading this blog if you don't comment! I don't have any analytics set up at all.
Update 16th Jan 2016: An anonymous commenter (please leave your name next time!) alerted me to a mistake in the test grading example. I've fixed it now, thank you!