22c:054 Team Projects

Validity Checker (SML, Miranda, Prolog, Oz)

Build a procedure for checking the validity of formulas in Propositional Logic. A validity checker is a predicate that takes a propositional formula as input and succeeds if and only if the formula is valid.

A simple (although rather inefficient) way to build a validity checker is described below. Before that, here is some background on propositional logic.

Propositional Variables

A propositional variable is a Boolean variable, that is, a variable whose only possible values are true or false. We denote propositional variables here by the small letters p, q, r, and so on.

Propositional Formulas

A propositional formula (or just formula) is an expression inductively defined as follows (we denote propositional variables here by the big letters F, G, H, and so on):

Satisfiable Formulas

A formula is satisfiable if there is an assignment of truth values to its propositional variables that makes it true (according to the truth table definition of the logical connectives ~,^,v,->,<->. The formula is unsatisfiable otherwise.

Valid Formula

A formula is valid if every assignment of truth values to its propositional variables that makes it true.

Examples

Literals

A propositional variable or a negated propositional variable is also called a literal.
Two literals are complementary if one is a propositional variable and the other is the negation of that variable.

For example, p and ~p are complementary.

Formula Conversions

The following formula conversions preserve satisfiability in the sense that a truth values assignment makes the formula before the conversion true if and only if it makes the formula after the conversion true.

1. F <-> G ==> (F -> G) ^ (G -> F)
2. F -> G ==> ~F v G
3. ~(~F) ==> F
4. ~(F v G) ==> ~F ^ ~G
5. ~(F ^ G) ==> ~F v ~G
6. F v (G ^ H) ==> (F v G) ^ (F v H)
7. (F ^ G) v H ==> (F v H) ^ (G v H)

Conversion into Conjunctive Normal Form

A formula is in Conjunctive Normal Form (CNF) is it is conjunction of disjunctions of literals.
Using the conversion rules above, it is possible to convert any formula into an equivalent one in Conjunctive Normal Form.

The procedure is composed of the following steps.

  1. Eliminate Double Implications.
    Recursively apply the conversion rule (1) above until all <-> connectives have been removed.

  2. Eliminate Implications.
    Recursively apply the conversion rule (2) above until all -> connectives have been removed.

  3. Move Negations Inside.
    Repeatedly apply the conversion rules (3), (4), (5) above until all the ~ connectives apply only to propositional variables.

  4. Distribute Disjunctions.
    Repeatedly apply the conversions rules (6), (7) above until no conjunctions are nested into a disjunction.

For instance, here is how the formula below gets converted into CNF:

(p ^ (q -> r)) -> s ==> (p ^ (~q v r)) -> s   by rule 2
==> ~(p ^ (~q v r)) v s   by rule 2
==> (~p v ~(~q v r)) v s   by rule 5
==> (~p v (~(~q) ^ ~r)) v s   by rule 4
==> (~p v (q ^ ~r)) v s   by rule 3
==> ((~p v q) ^ (~p v ~r)) v s   by rule 6
==> ((~p v q) v s) ^ ((~p v ~r) v s)   by rule 7

Conversion into List Normal Form

Every formula in Conjunctive Normal Form can be converted into a list of lists of literals. This is done by first turning the (possibly nested) conjunction into a (flat) list of disjunctions and then turning each (possibly nested) disjunction in the list into a (flat) list of literals.

For instance, the CNF formula

((p1 v ~p2) v (p3 v (p1 v ~p1))) ^ ((p3 v (~p1 v p4)) ^ ~p3)

is converted first into

[(p1 v ~p2) v (p3 v (p1 v ~p1)), p3 v (~p1 v p4), ~p3]

and then into

[[p1, ~p2, p3, p1, ~p1], [p3, ~p1 ,p4], [~p3]]

Deciding the Validity of Formulas

It is possible to show that a propositional formula is valid if and only if its List Normal Form is such that each of the inner lists contains two complementary literals.
(Can you prove that?)

Implementing the Validity Checker

Define an appropriate algebraic type (ML, Miranda) or term structure (Prolog, Oz) to represent propositional formulas. Then implement the decision procedure by writing code that first turns an input formula into list form, and then checks that every inner list contains two complementary literals, returning true if that is the case, and false otherwise.

In ML (the Miranda case is similar), you could define the fomula datatype with a definition of the form

datatype formula =V of string
|And of formula*formula
|Or of formula*formula
|...

Then, the formula p ^ (q v r), say, would be input in prefix form as the term

And(V("p"), Or(V("q"), V("r")))

In Prolog (the Oz case is similar), you do not need to define a specific type (and could not do it even if you wanted to). You can represent a formula such as p ^ (q v r), directly as the Prolog term

and(p, or(q, r))

 

Notice: In this problem propositional variables are pieces of data, they are not variables in the programming language you are using, Similarly, propositional formulas too are data, not boolean functions. You never evaluate them, you just manipulate them until they are in a certain format (List Normal Form) and then inspect them (looking for complementary literals).


Last Updated: Mar 8, 2000