theory HSV_tasks_2022 imports Complex_Main begin section {* Task 1: Full adders *} fun fulladder :: "bool * bool * bool \ bool * bool" where "fulladder (a,b,cin) = ( let (tmp1, tmp2) = halfadder(a,b) in let (tmp3, s) = halfadder(cin,tmp2) in let cout = tmp1 | tmp3 in (cout, s))" section {* Task 2: Fifth powers *} theorem "(n::nat) ^ 5 mod 10 = n mod 10" oops section {* Task 3: Logic optimisation *} (* Datatype for representing simple circuits. *) datatype "circuit" = NOT "circuit" | AND "circuit" "circuit" | OR "circuit" "circuit" | TRUE | FALSE | INPUT "int" (* Simulates a circuit given a valuation for each input wire. *) fun simulate where "simulate (AND c1 c2) \ = ((simulate c1 \) \ (simulate c2 \))" | "simulate (OR c1 c2) \ = ((simulate c1 \) \ (simulate c2 \))" | "simulate (NOT c) \ = (\ (simulate c \))" | "simulate TRUE \ = True" | "simulate FALSE \ = False" | "simulate (INPUT i) \ = \ i" (* Equivalence between circuits. *) fun circuits_equiv (infix "\" 50) (* the "50" indicates the operator precedence *) where "c1 \ c2 = (\\. simulate c1 \ = simulate c2 \)" (* An optimisation that exploits the following Boolean identities: `a | a = a` `a & a = a` *) fun opt_ident where "opt_ident (NOT c) = NOT (opt_ident c)" | "opt_ident (AND c1 c2) = ( let c1' = opt_ident c1 in let c2' = opt_ident c2 in if c1' = c2' then c1' else AND c1' c2')" | "opt_ident (OR c1 c2) = ( let c1' = opt_ident c1 in let c2' = opt_ident c2 in if c1' = c2' then c1' else OR c1' c2')" | "opt_ident TRUE = TRUE" | "opt_ident FALSE = FALSE" | "opt_ident (INPUT i) = INPUT i" lemma (* test case *) "opt_ident (AND (INPUT 1) (OR (INPUT 1) (INPUT 1))) = INPUT 1" by eval theorem opt_ident_is_sound: "opt_ident c \ c" oops fun area :: "circuit \ nat" where "area (NOT c) = 1 + area c" | "area (AND c1 c2) = 1 + area c1 + area c2" | "area (OR c1 c2) = 1 + area c1 + area c2" | "area _ = 0" section {* Task 4: More logic optimisation *} lemma (* test case *) "opt_redundancy (AND (INPUT 1) (OR (INPUT 1) (INPUT 2))) = INPUT 1" (* by eval *) oops lemma (* test case *) "opt_redundancy (AND (AND (INPUT 1) (OR (INPUT 1) (INPUT 2))) (OR (AND (INPUT 1) (OR (INPUT 1) (INPUT 2))) (INPUT 2))) = INPUT 1" (* by eval *) oops lemma (* test case *) "opt_redundancy (AND (AND (INPUT 1) (OR (INPUT 1) (INPUT 2))) (OR (INPUT 2) (AND (INPUT 1) (OR (INPUT 1) (INPUT 2))))) = INPUT 1" (* by eval *) oops lemma (* test case *) "opt_redundancy (AND (AND (AND (INPUT 1) (OR (INPUT 1) (INPUT 2))) (OR (INPUT 2) (AND (INPUT 1) (OR (INPUT 1) (INPUT 2))))) (OR (INPUT 1) (INPUT 2))) = INPUT 1" (* by eval *) oops end