All pastes #60016 Raw Edit

Unnamed

public text v1 · immutable
#60016 ·published 2006-05-30 19:06 UTC
rendered paste body
data Expr =
	Const Int
	| Add Expr Expr  -- a+b
	| Sub Expr Expr  -- a-b
	| Mul Expr Expr  -- a*b
	| Div Expr Expr  -- a/b (ganzzahlige Division)
	| Neg Expr       -- -a
	deriving (Eq, Show)

-- 1.1

{- 
Hier gibt es eigentlich nicht viel zu erklären...
Division durch 0 ist nicht definiert und Negation entspricht der Multiplikation
mit (-1) .
-}

eval :: Expr -> Int
eval (Const n) = n
eval (Add e1 e2) = (eval e1)+(eval e2)
eval (Sub e1 e2) = (eval e1)-(eval e2)
eval (Mul e1 e2) = (eval e1)*(eval e2)
eval (Div e1 (Const 0)) = error "Division durch 0 nicht definiert"
eval (Div e1 e2) = (eval e1) `div` (eval e2)
eval (Neg e1) = eval (Mul (Const (-1)) e1)

-- 1.2

{- 
Wir vereinbaren vorab:
Bei Negation und negativen Konstanten/Zahlen wird immer geklammert um klar zu machen,
dass eine negative Zahl gemeint ist bzw. um zu vermeiden, dass zwei Operatoren 
nebeneinanderstehen. (Also z.B. nicht: 5 * -9, sondern 5 * (-9)
Ansonsten gelten die "normalen" Prioritäten wie Punkt- vor Strichrechnung und, dass
Ausdrücke von links nach rechts ausgewertet werden.
( 3*4/5*6 entspricht ((3*4)/5)*6 )
-} 

getFormula :: Expr -> String

-- um den ganzen Term muss keine Klammer gemacht werde
-- immer wenn evtl. Punkt- vor Strichrechnung gilt, wird der "innere" Ausdruck
-- mit getKlammerFormula ausgwertet

getFormula (Const n) = if n<0 then "(" ++ show n ++ ")" else show n
getFormula (Add e1 e2) = getFormula e1 ++ "+" ++ getFormula e2 
getFormula (Sub e1 e2) = getFormula e1 ++ "-" ++ getKlammerFormula e2
getFormula (Mul e1 e2) = getKlammerFormula e1 ++ "*" ++ getKlammerFormula e2