2

I have the following:

type Name = String
data Prop
= Var Name
| F
| T
| Not Prop
| Prop :|: Prop
| Prop :&: Prop
deriving (Eq, Read)
infixr 2 :|:

the type Prop represents a propositional formula. The propositional variables, such as p and q can be represented by Var "p" and Var "q".

F and T are the constant booleans for False and True.

Not represents the negation (~ or ¬)

:|: and :&: represent the disjunction (/) and conjuction (/\)

We can write logical propositions:

( Var "p" :|: Var "q") :&: ( Not (Var "p") :&: Var "q")

What I have to do is: replace Not, :|: and :&: with ~, / and /\ by making Prop an instance of the class Show, so that the following will be true:

test_ShowProp :: Bool
test_ShowProp =
show (Not (Var "P") :&: Var "Q") == "((~P)/\Q)"

This is my implementation so far:

instance Show Prop where
    show (Var p) = p 
    show (Not (Var p)) = "(~" ++ p ++ ")" 
    show (Var p :|: Var q) = p ++ "\\/" ++ q
    show (Var p :&: Var q) = p ++ "/\\" ++ q

But this doesn't cover all the cases, just the basic ones. How should I continue the implementation so that it tackles any propositional formula, not just the hardcoded ones? Because at the moment

(Var "p" :&: Var "q")

outputs: p/\q

but

Not (Var "p" :&: Var "q")

outputs: Non-exhaustive patterns in function show

George Cernat
  • 1,323
  • 9
  • 27
  • I have a question, does Var "p" act as a replacement for the proposition p i.e. it can be T or F? Is the proposition ( Var "p" :|: Var "q") :&: ( Not (Var "p") :&: Var "q") satisfiable? – pranp2001 Nov 08 '22 at 13:33

2 Answers2

6

You should match only one "layer" of your formula, i.e. only one constructor, and exploit recursion for subformulae. For instance,

show (Not f) = "(~" ++ show f ++ ")"

will apply to any formula starting with a negation, even if there is a non variable subformula under that negation.

Getting parentheses right might be tricky. You'll need to either be generous with parentheses or define showsPrec. If you are a beginner, I'd recommend the former, which does not need to cope with precedence levels.

chi
  • 111,837
  • 3
  • 133
  • 218
3

You want to call show recursively in your definition. So the example with Not would be

show (Not p) = "(~" ++ show p ++ ")"
madgen
  • 747
  • 3
  • 15