doc-src/TutorialI/Ifexpr/Ifexpr.thy
changeset 9792 bbefb6ce5cb2
parent 9541 d17c0b34d5c8
child 9933 9feb1e0c4cb3
equal deleted inserted replaced
9791:a39e5d43de55 9792:bbefb6ce5cb2
    14                 | And boolex boolex;
    14                 | And boolex boolex;
    15 
    15 
    16 text{*\noindent
    16 text{*\noindent
    17 The two constants are represented by @{term"Const True"} and
    17 The two constants are represented by @{term"Const True"} and
    18 @{term"Const False"}. Variables are represented by terms of the form
    18 @{term"Const False"}. Variables are represented by terms of the form
    19 @{term"Var n"}, where @{term"n"} is a natural number (type \isa{nat}).
    19 @{term"Var n"}, where @{term"n"} is a natural number (type @{typ"nat"}).
    20 For example, the formula $P@0 \land \neg P@1$ is represented by the term
    20 For example, the formula $P@0 \land \neg P@1$ is represented by the term
    21 @{term"And (Var 0) (Neg(Var 1))"}.
    21 @{term"And (Var 0) (Neg(Var 1))"}.
    22 
    22 
    23 \subsubsection{What is the value of a boolean expression?}
    23 \subsubsection{What is the value of a boolean expression?}
    24 
    24 
    25 The value of a boolean expression depends on the value of its variables.
    25 The value of a boolean expression depends on the value of its variables.
    26 Hence the function \isa{value} takes an additional parameter, an {\em
    26 Hence the function @{text"value"} takes an additional parameter, an
    27   environment} of type @{typ"nat => bool"}, which maps variables to
    27 \emph{environment} of type @{typ"nat => bool"}, which maps variables to their
    28 their values:
    28 values:
    29 *}
    29 *}
    30 
    30 
    31 consts value :: "boolex \\<Rightarrow> (nat \\<Rightarrow> bool) \\<Rightarrow> bool";
    31 consts value :: "boolex \\<Rightarrow> (nat \\<Rightarrow> bool) \\<Rightarrow> bool";
    32 primrec
    32 primrec
    33 "value (Const b) env = b"
    33 "value (Const b) env = b"
    38 text{*\noindent
    38 text{*\noindent
    39 \subsubsection{If-expressions}
    39 \subsubsection{If-expressions}
    40 
    40 
    41 An alternative and often more efficient (because in a certain sense
    41 An alternative and often more efficient (because in a certain sense
    42 canonical) representation are so-called \emph{If-expressions} built up
    42 canonical) representation are so-called \emph{If-expressions} built up
    43 from constants (\isa{CIF}), variables (\isa{VIF}) and conditionals
    43 from constants (@{term"CIF"}), variables (@{term"VIF"}) and conditionals
    44 (\isa{IF}):
    44 (@{term"IF"}):
    45 *}
    45 *}
    46 
    46 
    47 datatype ifex = CIF bool | VIF nat | IF ifex ifex ifex;
    47 datatype ifex = CIF bool | VIF nat | IF ifex ifex ifex;
    48 
    48 
    49 text{*\noindent
    49 text{*\noindent
    50 The evaluation if If-expressions proceeds as for \isa{boolex}:
    50 The evaluation if If-expressions proceeds as for @{typ"boolex"}:
    51 *}
    51 *}
    52 
    52 
    53 consts valif :: "ifex \\<Rightarrow> (nat \\<Rightarrow> bool) \\<Rightarrow> bool";
    53 consts valif :: "ifex \\<Rightarrow> (nat \\<Rightarrow> bool) \\<Rightarrow> bool";
    54 primrec
    54 primrec
    55 "valif (CIF b)    env = b"
    55 "valif (CIF b)    env = b"
    58                                         else valif e env)";
    58                                         else valif e env)";
    59 
    59 
    60 text{*
    60 text{*
    61 \subsubsection{Transformation into and of If-expressions}
    61 \subsubsection{Transformation into and of If-expressions}
    62 
    62 
    63 The type \isa{boolex} is close to the customary representation of logical
    63 The type @{typ"boolex"} is close to the customary representation of logical
    64 formulae, whereas \isa{ifex} is designed for efficiency. It is easy to
    64 formulae, whereas @{typ"ifex"} is designed for efficiency. It is easy to
    65 translate from \isa{boolex} into \isa{ifex}:
    65 translate from @{typ"boolex"} into @{typ"ifex"}:
    66 *}
    66 *}
    67 
    67 
    68 consts bool2if :: "boolex \\<Rightarrow> ifex";
    68 consts bool2if :: "boolex \\<Rightarrow> ifex";
    69 primrec
    69 primrec
    70 "bool2if (Const b) = CIF b"
    70 "bool2if (Const b) = CIF b"
    71 "bool2if (Var x)   = VIF x"
    71 "bool2if (Var x)   = VIF x"
    72 "bool2if (Neg b)   = IF (bool2if b) (CIF False) (CIF True)"
    72 "bool2if (Neg b)   = IF (bool2if b) (CIF False) (CIF True)"
    73 "bool2if (And b c) = IF (bool2if b) (bool2if c) (CIF False)";
    73 "bool2if (And b c) = IF (bool2if b) (bool2if c) (CIF False)";
    74 
    74 
    75 text{*\noindent
    75 text{*\noindent
    76 At last, we have something we can verify: that \isa{bool2if} preserves the
    76 At last, we have something we can verify: that @{term"bool2if"} preserves the
    77 value of its argument:
    77 value of its argument:
    78 *}
    78 *}
    79 
    79 
    80 lemma "valif (bool2if b) env = value b env";
    80 lemma "valif (bool2if b) env = value b env";
    81 
    81 
    89 text{*\noindent
    89 text{*\noindent
    90 In fact, all proofs in this case study look exactly like this. Hence we do
    90 In fact, all proofs in this case study look exactly like this. Hence we do
    91 not show them below.
    91 not show them below.
    92 
    92 
    93 More interesting is the transformation of If-expressions into a normal form
    93 More interesting is the transformation of If-expressions into a normal form
    94 where the first argument of \isa{IF} cannot be another \isa{IF} but
    94 where the first argument of @{term"IF"} cannot be another @{term"IF"} but
    95 must be a constant or variable. Such a normal form can be computed by
    95 must be a constant or variable. Such a normal form can be computed by
    96 repeatedly replacing a subterm of the form @{term"IF (IF b x y) z u"} by
    96 repeatedly replacing a subterm of the form @{term"IF (IF b x y) z u"} by
    97 @{term"IF b (IF x z u) (IF y z u)"}, which has the same value. The following
    97 @{term"IF b (IF x z u) (IF y z u)"}, which has the same value. The following
    98 primitive recursive functions perform this task:
    98 primitive recursive functions perform this task:
    99 *}
    99 *}
   118 
   118 
   119 theorem "valif (norm b) env = valif b env";(*<*)oops;(*>*)
   119 theorem "valif (norm b) env = valif b env";(*<*)oops;(*>*)
   120 
   120 
   121 text{*\noindent
   121 text{*\noindent
   122 The proof is canonical, provided we first show the following simplification
   122 The proof is canonical, provided we first show the following simplification
   123 lemma (which also helps to understand what \isa{normif} does):
   123 lemma (which also helps to understand what @{term"normif"} does):
   124 *}
   124 *}
   125 
   125 
   126 lemma [simp]:
   126 lemma [simp]:
   127   "\\<forall>t e. valif (normif b t e) env = valif (IF b t e) env";
   127   "\\<forall>t e. valif (normif b t e) env = valif (IF b t e) env";
   128 (*<*)
   128 (*<*)
   133 apply(induct_tac b);
   133 apply(induct_tac b);
   134 by(auto);
   134 by(auto);
   135 (*>*)
   135 (*>*)
   136 text{*\noindent
   136 text{*\noindent
   137 Note that the lemma does not have a name, but is implicitly used in the proof
   137 Note that the lemma does not have a name, but is implicitly used in the proof
   138 of the theorem shown above because of the \isa{[simp]} attribute.
   138 of the theorem shown above because of the @{text"[simp]"} attribute.
   139 
   139 
   140 But how can we be sure that \isa{norm} really produces a normal form in
   140 But how can we be sure that @{term"norm"} really produces a normal form in
   141 the above sense? We define a function that tests If-expressions for normality
   141 the above sense? We define a function that tests If-expressions for normality
   142 *}
   142 *}
   143 
   143 
   144 consts normal :: "ifex \\<Rightarrow> bool";
   144 consts normal :: "ifex \\<Rightarrow> bool";
   145 primrec
   145 primrec
   147 "normal(VIF x) = True"
   147 "normal(VIF x) = True"
   148 "normal(IF b t e) = (normal t \\<and> normal e \\<and>
   148 "normal(IF b t e) = (normal t \\<and> normal e \\<and>
   149      (case b of CIF b \\<Rightarrow> True | VIF x \\<Rightarrow> True | IF x y z \\<Rightarrow> False))";
   149      (case b of CIF b \\<Rightarrow> True | VIF x \\<Rightarrow> True | IF x y z \\<Rightarrow> False))";
   150 
   150 
   151 text{*\noindent
   151 text{*\noindent
   152 and prove \isa{normal(norm b)}. Of course, this requires a lemma about
   152 and prove @{term"normal(norm b)"}. Of course, this requires a lemma about
   153 normality of \isa{normif}:
   153 normality of @{term"normif"}:
   154 *}
   154 *}
   155 
   155 
   156 lemma[simp]: "\\<forall>t e. normal(normif b t e) = (normal t \\<and> normal e)";
   156 lemma[simp]: "\\<forall>t e. normal(normif b t e) = (normal t \\<and> normal e)";
   157 (*<*)
   157 (*<*)
   158 apply(induct_tac b);
   158 apply(induct_tac b);