src/HOL/ex/Fundefs.thy
changeset 21240 8e75fb38522c
parent 21051 c49467a9c1e1
child 21319 cf814e36f788
equal deleted inserted replaced
21239:d4fbe2c87ef1 21240:8e75fb38522c
    27 
    27 
    28 thm fib.domintros
    28 thm fib.domintros
    29 
    29 
    30 
    30 
    31 text {* Now termination: *}
    31 text {* Now termination: *}
    32 termination fib
    32 (*termination fib
    33   by (auto_term "less_than")
    33   by (auto_term "less_than")*)
    34 
    34 
    35 thm fib.simps
    35 thm fib.simps
    36 thm fib.induct
    36 thm fib.induct
    37 
    37 
    38 
    38 
    40 
    40 
    41 fun add :: "nat \<Rightarrow> nat \<Rightarrow> nat"
    41 fun add :: "nat \<Rightarrow> nat \<Rightarrow> nat"
    42 where
    42 where
    43   "add 0 y = y"
    43   "add 0 y = y"
    44 | "add (Suc x) y = Suc (add x y)"
    44 | "add (Suc x) y = Suc (add x y)"
    45 termination
       
    46   by (auto_term "measure fst")
       
    47 
    45 
    48 thm add.simps
    46 thm add.simps
    49 thm add.induct -- {* Note the curried induction predicate *}
    47 thm add.induct -- {* Note the curried induction predicate *}
    50 
    48 
    51 
    49 
    52 section {* Nested recursion *}
    50 section {* Nested recursion *}
    53 
    51 
    54 fun nz :: "nat \<Rightarrow> nat"
    52 function nz :: "nat \<Rightarrow> nat"
    55 where
    53 where
    56   "nz 0 = 0"
    54   "nz 0 = 0"
    57 | "nz (Suc x) = nz (nz x)"
    55 | "nz (Suc x) = nz (nz x)"
       
    56 by pat_completeness auto
    58 
    57 
    59 lemma nz_is_zero: -- {* A lemma we need to prove termination *}
    58 lemma nz_is_zero: -- {* A lemma we need to prove termination *}
    60   assumes trm: "nz_dom x"
    59   assumes trm: "nz_dom x"
    61   shows "nz x = 0"
    60   shows "nz x = 0"
    62 using trm
    61 using trm
    70 thm nz.induct
    69 thm nz.induct
    71 
    70 
    72 text {* Here comes McCarthy's 91-function *}
    71 text {* Here comes McCarthy's 91-function *}
    73 
    72 
    74 
    73 
    75 fun f91 :: "nat => nat"
    74 function f91 :: "nat => nat"
    76 where
    75 where
    77   "f91 n = (if 100 < n then n - 10 else f91 (f91 (n + 11)))"
    76   "f91 n = (if 100 < n then n - 10 else f91 (f91 (n + 11)))"
       
    77 by pat_completeness auto
    78 
    78 
    79 (* Prove a lemma before attempting a termination proof *)
    79 (* Prove a lemma before attempting a termination proof *)
    80 lemma f91_estimate: 
    80 lemma f91_estimate: 
    81   assumes trm: "f91_dom n" 
    81   assumes trm: "f91_dom n" 
    82   shows "n < f91 n + 11"
    82   shows "n < f91 n + 11"
   110   "gcd2 x 0 = x"
   110   "gcd2 x 0 = x"
   111 | "gcd2 0 y = y"
   111 | "gcd2 0 y = y"
   112 | "gcd2 (Suc x) (Suc y) = (if x < y then gcd2 (Suc x) (y - x)
   112 | "gcd2 (Suc x) (Suc y) = (if x < y then gcd2 (Suc x) (y - x)
   113                                     else gcd2 (x - y) (Suc y))"
   113                                     else gcd2 (x - y) (Suc y))"
   114 
   114 
   115 
       
   116 termination 
       
   117   by (auto_term "(measure (%x. x)) <*lex*> (measure (%x. x))")
       
   118 
       
   119 thm gcd2.simps
   115 thm gcd2.simps
   120 thm gcd2.induct
   116 thm gcd2.induct
   121 
   117 
   122 subsection {* Guards *}
   118 subsection {* Guards *}
   123 
   119 
   130   "x < y \<Longrightarrow> gcd3 (Suc x) (Suc y) = gcd3 (Suc x) (y - x)"
   126   "x < y \<Longrightarrow> gcd3 (Suc x) (Suc y) = gcd3 (Suc x) (y - x)"
   131   "\<not> x < y \<Longrightarrow> gcd3 (Suc x) (Suc y) = gcd3 (x - y) (Suc y)"
   127   "\<not> x < y \<Longrightarrow> gcd3 (Suc x) (Suc y) = gcd3 (x - y) (Suc y)"
   132   apply (case_tac x, case_tac a, auto)
   128   apply (case_tac x, case_tac a, auto)
   133   apply (case_tac ba, auto)
   129   apply (case_tac ba, auto)
   134   done
   130   done
   135 
   131 termination by lexicographic_order
   136 termination 
       
   137   by (auto_term "measure (\<lambda>(x,y). x + y)")
       
   138 
   132 
   139 thm gcd3.simps
   133 thm gcd3.simps
   140 thm gcd3.induct
   134 thm gcd3.induct
   141 
   135 
   142 
   136 
   162     hence "x mod 2 = 1" by simp
   156     hence "x mod 2 = 1" by simp
   163     with divmod have "x = 2 * (x div 2) + 1" by simp
   157     with divmod have "x = 2 * (x div 2) + 1" by simp
   164     with c2 show "P" .
   158     with c2 show "P" .
   165   qed
   159   qed
   166 qed presburger+ -- {* solve compatibility with presburger *}
   160 qed presburger+ -- {* solve compatibility with presburger *}
   167 termination by (auto_term "{}")
   161 termination by lexicographic_order
   168 
   162 
   169 thm ev.simps
   163 thm ev.simps
   170 thm ev.induct
   164 thm ev.induct
   171 thm ev.cases
   165 thm ev.cases
   172 
   166 
   178   "evn 0 = True"
   172   "evn 0 = True"
   179 | "od 0 = False"
   173 | "od 0 = False"
   180 | "evn (Suc n) = od n"
   174 | "evn (Suc n) = od n"
   181 | "od (Suc n) = evn n"
   175 | "od (Suc n) = evn n"
   182 
   176 
   183 thm evn.psimps
   177 thm evn.simps
   184 thm od.psimps
   178 thm od.simps
   185 
   179 
   186 thm evn_od.pinduct
   180 thm evn_od.pinduct
   187 thm evn_od.termination
   181 thm evn_od.termination
   188 thm evn_od.domintros
   182 thm evn_od.domintros
   189 
   183 
   190 termination
       
   191   by (auto_term "measure (sum_case (%n. n) (%n. n))")
       
   192 
   184 
   193 thm evn.simps
   185 
   194 thm od.simps
       
   195 
   186 
   196 
   187 
   197 end
   188 end