src/HOL/Decision_Procs/MIR.thy
author huffman
Sun Apr 01 16:09:58 2012 +0200 (2012-04-01)
changeset 47255 30a1692557b0
parent 47142 d64fa2ca54b8
child 47432 e1576d13e933
permissions -rw-r--r--
removed Nat_Numeral.thy, moving all theorems elsewhere
     1 (*  Title:      HOL/Decision_Procs/MIR.thy
     2     Author:     Amine Chaieb
     3 *)
     4 
     5 theory MIR
     6 imports Complex_Main Dense_Linear_Order DP_Library
     7   "~~/src/HOL/Library/Efficient_Nat" "~~/src/HOL/Library/Old_Recdef"
     8 uses ("mir_tac.ML")
     9 begin
    10 
    11 section {* Quantifier elimination for @{text "\<real> (0, 1, +, floor, <)"} *}
    12 
    13 declare real_of_int_floor_cancel [simp del]
    14 
    15 lemma myle: fixes a b :: "'a::{ordered_ab_group_add}"
    16   shows "(a \<le> b) = (0 \<le> b - a)"
    17 by (metis add_0_left add_le_cancel_right diff_add_cancel)
    18 
    19 lemma myless: fixes a b :: "'a::{ordered_ab_group_add}"
    20   shows "(a < b) = (0 < b - a)"
    21 by (metis le_iff_diff_le_0 less_le_not_le myle)
    22 
    23   (* Maybe should be added to the library \<dots> *)
    24 lemma floor_int_eq: "(real n\<le> x \<and> x < real (n+1)) = (floor x = n)"
    25 proof( auto)
    26   assume lb: "real n \<le> x"
    27     and ub: "x < real n + 1"
    28   have "real (floor x) \<le> x" by simp 
    29   hence "real (floor x) < real (n + 1) " using ub by arith
    30   hence "floor x < n+1" by simp
    31   moreover from lb have "n \<le> floor x" using floor_mono[where x="real n" and y="x"] 
    32     by simp ultimately show "floor x = n" by simp
    33 qed
    34 
    35 (* Periodicity of dvd *)
    36 lemma dvd_period:
    37   assumes advdd: "(a::int) dvd d"
    38   shows "(a dvd (x + t)) = (a dvd ((x+ c*d) + t))"
    39   using advdd  
    40 proof-
    41   {fix x k
    42     from inf_period(3)[OF advdd, rule_format, where x=x and k="-k"]  
    43     have " ((a::int) dvd (x + t)) = (a dvd (x+k*d + t))" by simp}
    44   hence "\<forall>x.\<forall>k. ((a::int) dvd (x + t)) = (a dvd (x+k*d + t))"  by simp
    45   then show ?thesis by simp
    46 qed
    47 
    48 (* The Divisibility relation between reals *)
    49 definition
    50   rdvd:: "real \<Rightarrow> real \<Rightarrow> bool" (infixl "rdvd" 50)
    51 where
    52   rdvd_def: "x rdvd y \<longleftrightarrow> (\<exists>k\<Colon>int. y = x * real k)"
    53 
    54 lemma int_rdvd_real: 
    55   shows "real (i::int) rdvd x = (i dvd (floor x) \<and> real (floor x) = x)" (is "?l = ?r")
    56 proof
    57   assume "?l" 
    58   hence th: "\<exists> k. x=real (i*k)" by (simp add: rdvd_def)
    59   hence th': "real (floor x) = x" by (auto simp del: real_of_int_mult)
    60   with th have "\<exists> k. real (floor x) = real (i*k)" by simp
    61   hence "\<exists> k. floor x = i*k" by (simp only: real_of_int_inject)
    62   thus ?r  using th' by (simp add: dvd_def) 
    63 next
    64   assume "?r" hence "(i\<Colon>int) dvd \<lfloor>x\<Colon>real\<rfloor>" ..
    65   hence "\<exists> k. real (floor x) = real (i*k)" 
    66     by (simp only: real_of_int_inject) (simp add: dvd_def)
    67   thus ?l using `?r` by (simp add: rdvd_def)
    68 qed
    69 
    70 lemma int_rdvd_iff: "(real (i::int) rdvd real t) = (i dvd t)"
    71 by (auto simp add: rdvd_def dvd_def) (rule_tac x="k" in exI, simp only :real_of_int_mult[symmetric])
    72 
    73 
    74 lemma rdvd_abs1: 
    75   "(abs (real d) rdvd t) = (real (d ::int) rdvd t)"
    76 proof
    77   assume d: "real d rdvd t"
    78   from d int_rdvd_real have d2: "d dvd (floor t)" and ti: "real (floor t) = t" by auto
    79 
    80   from iffD2[OF abs_dvd_iff] d2 have "(abs d) dvd (floor t)" by blast
    81   with ti int_rdvd_real[symmetric] have "real (abs d) rdvd t" by blast 
    82   thus "abs (real d) rdvd t" by simp
    83 next
    84   assume "abs (real d) rdvd t" hence "real (abs d) rdvd t" by simp
    85   with int_rdvd_real[where i="abs d" and x="t"] have d2: "abs d dvd floor t" and ti: "real (floor t) =t" by auto
    86   from iffD1[OF abs_dvd_iff] d2 have "d dvd floor t" by blast
    87   with ti int_rdvd_real[symmetric] show "real d rdvd t" by blast
    88 qed
    89 
    90 lemma rdvd_minus: "(real (d::int) rdvd t) = (real d rdvd -t)"
    91   apply (auto simp add: rdvd_def)
    92   apply (rule_tac x="-k" in exI, simp) 
    93   apply (rule_tac x="-k" in exI, simp)
    94 done
    95 
    96 lemma rdvd_left_0_eq: "(0 rdvd t) = (t=0)"
    97 by (auto simp add: rdvd_def)
    98 
    99 lemma rdvd_mult: 
   100   assumes knz: "k\<noteq>0"
   101   shows "(real (n::int) * real (k::int) rdvd x * real k) = (real n rdvd x)"
   102 using knz by (simp add:rdvd_def)
   103 
   104   (*********************************************************************************)
   105   (****                            SHADOW SYNTAX AND SEMANTICS                  ****)
   106   (*********************************************************************************)
   107 
   108 datatype num = C int | Bound nat | CN nat int num | Neg num | Add num num| Sub num num 
   109   | Mul int num | Floor num| CF int num num
   110 
   111   (* A size for num to make inductive proofs simpler*)
   112 primrec num_size :: "num \<Rightarrow> nat" where
   113  "num_size (C c) = 1"
   114 | "num_size (Bound n) = 1"
   115 | "num_size (Neg a) = 1 + num_size a"
   116 | "num_size (Add a b) = 1 + num_size a + num_size b"
   117 | "num_size (Sub a b) = 3 + num_size a + num_size b"
   118 | "num_size (CN n c a) = 4 + num_size a "
   119 | "num_size (CF c a b) = 4 + num_size a + num_size b"
   120 | "num_size (Mul c a) = 1 + num_size a"
   121 | "num_size (Floor a) = 1 + num_size a"
   122 
   123   (* Semantics of numeral terms (num) *)
   124 primrec Inum :: "real list \<Rightarrow> num \<Rightarrow> real" where
   125   "Inum bs (C c) = (real c)"
   126 | "Inum bs (Bound n) = bs!n"
   127 | "Inum bs (CN n c a) = (real c) * (bs!n) + (Inum bs a)"
   128 | "Inum bs (Neg a) = -(Inum bs a)"
   129 | "Inum bs (Add a b) = Inum bs a + Inum bs b"
   130 | "Inum bs (Sub a b) = Inum bs a - Inum bs b"
   131 | "Inum bs (Mul c a) = (real c) * Inum bs a"
   132 | "Inum bs (Floor a) = real (floor (Inum bs a))"
   133 | "Inum bs (CF c a b) = real c * real (floor (Inum bs a)) + Inum bs b"
   134 definition "isint t bs \<equiv> real (floor (Inum bs t)) = Inum bs t"
   135 
   136 lemma isint_iff: "isint n bs = (real (floor (Inum bs n)) = Inum bs n)"
   137 by (simp add: isint_def)
   138 
   139 lemma isint_Floor: "isint (Floor n) bs"
   140   by (simp add: isint_iff)
   141 
   142 lemma isint_Mul: "isint e bs \<Longrightarrow> isint (Mul c e) bs"
   143 proof-
   144   let ?e = "Inum bs e"
   145   let ?fe = "floor ?e"
   146   assume be: "isint e bs" hence efe:"real ?fe = ?e" by (simp add: isint_iff)
   147   have "real ((floor (Inum bs (Mul c e)))) = real (floor (real (c * ?fe)))" using efe by simp
   148   also have "\<dots> = real (c* ?fe)" by (simp only: floor_real_of_int) 
   149   also have "\<dots> = real c * ?e" using efe by simp
   150   finally show ?thesis using isint_iff by simp
   151 qed
   152 
   153 lemma isint_neg: "isint e bs \<Longrightarrow> isint (Neg e) bs"
   154 proof-
   155   let ?I = "\<lambda> t. Inum bs t"
   156   assume ie: "isint e bs"
   157   hence th: "real (floor (?I e)) = ?I e" by (simp add: isint_def)  
   158   have "real (floor (?I (Neg e))) = real (floor (- (real (floor (?I e)))))" by (simp add: th)
   159   also have "\<dots> = - real (floor (?I e))" by(simp add: floor_minus_real_of_int) 
   160   finally show "isint (Neg e) bs" by (simp add: isint_def th)
   161 qed
   162 
   163 lemma isint_sub: 
   164   assumes ie: "isint e bs" shows "isint (Sub (C c) e) bs"
   165 proof-
   166   let ?I = "\<lambda> t. Inum bs t"
   167   from ie have th: "real (floor (?I e)) = ?I e" by (simp add: isint_def)  
   168   have "real (floor (?I (Sub (C c) e))) = real (floor ((real (c -floor (?I e)))))" by (simp add: th)
   169   also have "\<dots> = real (c- floor (?I e))" by(simp add: floor_minus_real_of_int) 
   170   finally show "isint (Sub (C c) e) bs" by (simp add: isint_def th)
   171 qed
   172 
   173 lemma isint_add: assumes
   174   ai:"isint a bs" and bi: "isint b bs" shows "isint (Add a b) bs"
   175 proof-
   176   let ?a = "Inum bs a"
   177   let ?b = "Inum bs b"
   178   from ai bi isint_iff have "real (floor (?a + ?b)) = real (floor (real (floor ?a) + real (floor ?b)))" by simp
   179   also have "\<dots> = real (floor ?a) + real (floor ?b)" by simp
   180   also have "\<dots> = ?a + ?b" using ai bi isint_iff by simp
   181   finally show "isint (Add a b) bs" by (simp add: isint_iff)
   182 qed
   183 
   184 lemma isint_c: "isint (C j) bs"
   185   by (simp add: isint_iff)
   186 
   187 
   188     (* FORMULAE *)
   189 datatype fm  = 
   190   T| F| Lt num| Le num| Gt num| Ge num| Eq num| NEq num| Dvd int num| NDvd int num|
   191   NOT fm| And fm fm|  Or fm fm| Imp fm fm| Iff fm fm| E fm| A fm
   192 
   193 
   194   (* A size for fm *)
   195 fun fmsize :: "fm \<Rightarrow> nat" where
   196  "fmsize (NOT p) = 1 + fmsize p"
   197 | "fmsize (And p q) = 1 + fmsize p + fmsize q"
   198 | "fmsize (Or p q) = 1 + fmsize p + fmsize q"
   199 | "fmsize (Imp p q) = 3 + fmsize p + fmsize q"
   200 | "fmsize (Iff p q) = 3 + 2*(fmsize p + fmsize q)"
   201 | "fmsize (E p) = 1 + fmsize p"
   202 | "fmsize (A p) = 4+ fmsize p"
   203 | "fmsize (Dvd i t) = 2"
   204 | "fmsize (NDvd i t) = 2"
   205 | "fmsize p = 1"
   206   (* several lemmas about fmsize *)
   207 lemma fmsize_pos: "fmsize p > 0"
   208 by (induct p rule: fmsize.induct) simp_all
   209 
   210   (* Semantics of formulae (fm) *)
   211 primrec Ifm ::"real list \<Rightarrow> fm \<Rightarrow> bool" where
   212   "Ifm bs T = True"
   213 | "Ifm bs F = False"
   214 | "Ifm bs (Lt a) = (Inum bs a < 0)"
   215 | "Ifm bs (Gt a) = (Inum bs a > 0)"
   216 | "Ifm bs (Le a) = (Inum bs a \<le> 0)"
   217 | "Ifm bs (Ge a) = (Inum bs a \<ge> 0)"
   218 | "Ifm bs (Eq a) = (Inum bs a = 0)"
   219 | "Ifm bs (NEq a) = (Inum bs a \<noteq> 0)"
   220 | "Ifm bs (Dvd i b) = (real i rdvd Inum bs b)"
   221 | "Ifm bs (NDvd i b) = (\<not>(real i rdvd Inum bs b))"
   222 | "Ifm bs (NOT p) = (\<not> (Ifm bs p))"
   223 | "Ifm bs (And p q) = (Ifm bs p \<and> Ifm bs q)"
   224 | "Ifm bs (Or p q) = (Ifm bs p \<or> Ifm bs q)"
   225 | "Ifm bs (Imp p q) = ((Ifm bs p) \<longrightarrow> (Ifm bs q))"
   226 | "Ifm bs (Iff p q) = (Ifm bs p = Ifm bs q)"
   227 | "Ifm bs (E p) = (\<exists> x. Ifm (x#bs) p)"
   228 | "Ifm bs (A p) = (\<forall> x. Ifm (x#bs) p)"
   229 
   230 consts prep :: "fm \<Rightarrow> fm"
   231 recdef prep "measure fmsize"
   232   "prep (E T) = T"
   233   "prep (E F) = F"
   234   "prep (E (Or p q)) = Or (prep (E p)) (prep (E q))"
   235   "prep (E (Imp p q)) = Or (prep (E (NOT p))) (prep (E q))"
   236   "prep (E (Iff p q)) = Or (prep (E (And p q))) (prep (E (And (NOT p) (NOT q))))" 
   237   "prep (E (NOT (And p q))) = Or (prep (E (NOT p))) (prep (E(NOT q)))"
   238   "prep (E (NOT (Imp p q))) = prep (E (And p (NOT q)))"
   239   "prep (E (NOT (Iff p q))) = Or (prep (E (And p (NOT q)))) (prep (E(And (NOT p) q)))"
   240   "prep (E p) = E (prep p)"
   241   "prep (A (And p q)) = And (prep (A p)) (prep (A q))"
   242   "prep (A p) = prep (NOT (E (NOT p)))"
   243   "prep (NOT (NOT p)) = prep p"
   244   "prep (NOT (And p q)) = Or (prep (NOT p)) (prep (NOT q))"
   245   "prep (NOT (A p)) = prep (E (NOT p))"
   246   "prep (NOT (Or p q)) = And (prep (NOT p)) (prep (NOT q))"
   247   "prep (NOT (Imp p q)) = And (prep p) (prep (NOT q))"
   248   "prep (NOT (Iff p q)) = Or (prep (And p (NOT q))) (prep (And (NOT p) q))"
   249   "prep (NOT p) = NOT (prep p)"
   250   "prep (Or p q) = Or (prep p) (prep q)"
   251   "prep (And p q) = And (prep p) (prep q)"
   252   "prep (Imp p q) = prep (Or (NOT p) q)"
   253   "prep (Iff p q) = Or (prep (And p q)) (prep (And (NOT p) (NOT q)))"
   254   "prep p = p"
   255 (hints simp add: fmsize_pos)
   256 lemma prep: "\<And> bs. Ifm bs (prep p) = Ifm bs p"
   257 by (induct p rule: prep.induct, auto)
   258 
   259 
   260   (* Quantifier freeness *)
   261 fun qfree:: "fm \<Rightarrow> bool" where
   262   "qfree (E p) = False"
   263   | "qfree (A p) = False"
   264   | "qfree (NOT p) = qfree p" 
   265   | "qfree (And p q) = (qfree p \<and> qfree q)" 
   266   | "qfree (Or  p q) = (qfree p \<and> qfree q)" 
   267   | "qfree (Imp p q) = (qfree p \<and> qfree q)" 
   268   | "qfree (Iff p q) = (qfree p \<and> qfree q)"
   269   | "qfree p = True"
   270 
   271   (* Boundedness and substitution *)
   272 primrec numbound0 :: "num \<Rightarrow> bool" (* a num is INDEPENDENT of Bound 0 *) where
   273   "numbound0 (C c) = True"
   274   | "numbound0 (Bound n) = (n>0)"
   275   | "numbound0 (CN n i a) = (n > 0 \<and> numbound0 a)"
   276   | "numbound0 (Neg a) = numbound0 a"
   277   | "numbound0 (Add a b) = (numbound0 a \<and> numbound0 b)"
   278   | "numbound0 (Sub a b) = (numbound0 a \<and> numbound0 b)" 
   279   | "numbound0 (Mul i a) = numbound0 a"
   280   | "numbound0 (Floor a) = numbound0 a"
   281   | "numbound0 (CF c a b) = (numbound0 a \<and> numbound0 b)" 
   282 
   283 lemma numbound0_I:
   284   assumes nb: "numbound0 a"
   285   shows "Inum (b#bs) a = Inum (b'#bs) a"
   286   using nb by (induct a) auto
   287 
   288 lemma numbound0_gen: 
   289   assumes nb: "numbound0 t" and ti: "isint t (x#bs)"
   290   shows "\<forall> y. isint t (y#bs)"
   291 using nb ti 
   292 proof(clarify)
   293   fix y
   294   from numbound0_I[OF nb, where bs="bs" and b="y" and b'="x"] ti[simplified isint_def]
   295   show "isint t (y#bs)"
   296     by (simp add: isint_def)
   297 qed
   298 
   299 primrec bound0:: "fm \<Rightarrow> bool" (* A Formula is independent of Bound 0 *) where
   300   "bound0 T = True"
   301   | "bound0 F = True"
   302   | "bound0 (Lt a) = numbound0 a"
   303   | "bound0 (Le a) = numbound0 a"
   304   | "bound0 (Gt a) = numbound0 a"
   305   | "bound0 (Ge a) = numbound0 a"
   306   | "bound0 (Eq a) = numbound0 a"
   307   | "bound0 (NEq a) = numbound0 a"
   308   | "bound0 (Dvd i a) = numbound0 a"
   309   | "bound0 (NDvd i a) = numbound0 a"
   310   | "bound0 (NOT p) = bound0 p"
   311   | "bound0 (And p q) = (bound0 p \<and> bound0 q)"
   312   | "bound0 (Or p q) = (bound0 p \<and> bound0 q)"
   313   | "bound0 (Imp p q) = ((bound0 p) \<and> (bound0 q))"
   314   | "bound0 (Iff p q) = (bound0 p \<and> bound0 q)"
   315   | "bound0 (E p) = False"
   316   | "bound0 (A p) = False"
   317 
   318 lemma bound0_I:
   319   assumes bp: "bound0 p"
   320   shows "Ifm (b#bs) p = Ifm (b'#bs) p"
   321  using bp numbound0_I [where b="b" and bs="bs" and b'="b'"]
   322   by (induct p) auto
   323 
   324 primrec numsubst0:: "num \<Rightarrow> num \<Rightarrow> num" (* substitute a num into a num for Bound 0 *) where
   325   "numsubst0 t (C c) = (C c)"
   326   | "numsubst0 t (Bound n) = (if n=0 then t else Bound n)"
   327   | "numsubst0 t (CN n i a) = (if n=0 then Add (Mul i t) (numsubst0 t a) else CN n i (numsubst0 t a))"
   328   | "numsubst0 t (CF i a b) = CF i (numsubst0 t a) (numsubst0 t b)"
   329   | "numsubst0 t (Neg a) = Neg (numsubst0 t a)"
   330   | "numsubst0 t (Add a b) = Add (numsubst0 t a) (numsubst0 t b)"
   331   | "numsubst0 t (Sub a b) = Sub (numsubst0 t a) (numsubst0 t b)" 
   332   | "numsubst0 t (Mul i a) = Mul i (numsubst0 t a)"
   333   | "numsubst0 t (Floor a) = Floor (numsubst0 t a)"
   334 
   335 lemma numsubst0_I:
   336   shows "Inum (b#bs) (numsubst0 a t) = Inum ((Inum (b#bs) a)#bs) t"
   337   by (induct t) simp_all
   338 
   339 primrec subst0:: "num \<Rightarrow> fm \<Rightarrow> fm" (* substitue a num into a formula for Bound 0 *) where
   340   "subst0 t T = T"
   341   | "subst0 t F = F"
   342   | "subst0 t (Lt a) = Lt (numsubst0 t a)"
   343   | "subst0 t (Le a) = Le (numsubst0 t a)"
   344   | "subst0 t (Gt a) = Gt (numsubst0 t a)"
   345   | "subst0 t (Ge a) = Ge (numsubst0 t a)"
   346   | "subst0 t (Eq a) = Eq (numsubst0 t a)"
   347   | "subst0 t (NEq a) = NEq (numsubst0 t a)"
   348   | "subst0 t (Dvd i a) = Dvd i (numsubst0 t a)"
   349   | "subst0 t (NDvd i a) = NDvd i (numsubst0 t a)"
   350   | "subst0 t (NOT p) = NOT (subst0 t p)"
   351   | "subst0 t (And p q) = And (subst0 t p) (subst0 t q)"
   352   | "subst0 t (Or p q) = Or (subst0 t p) (subst0 t q)"
   353   | "subst0 t (Imp p q) = Imp (subst0 t p) (subst0 t q)"
   354   | "subst0 t (Iff p q) = Iff (subst0 t p) (subst0 t q)"
   355 
   356 lemma subst0_I: assumes qfp: "qfree p"
   357   shows "Ifm (b#bs) (subst0 a p) = Ifm ((Inum (b#bs) a)#bs) p"
   358   using qfp numsubst0_I[where b="b" and bs="bs" and a="a"]
   359   by (induct p) simp_all
   360 
   361 fun decrnum:: "num \<Rightarrow> num" where
   362   "decrnum (Bound n) = Bound (n - 1)"
   363 | "decrnum (Neg a) = Neg (decrnum a)"
   364 | "decrnum (Add a b) = Add (decrnum a) (decrnum b)"
   365 | "decrnum (Sub a b) = Sub (decrnum a) (decrnum b)"
   366 | "decrnum (Mul c a) = Mul c (decrnum a)"
   367 | "decrnum (Floor a) = Floor (decrnum a)"
   368 | "decrnum (CN n c a) = CN (n - 1) c (decrnum a)"
   369 | "decrnum (CF c a b) = CF c (decrnum a) (decrnum b)"
   370 | "decrnum a = a"
   371 
   372 fun decr :: "fm \<Rightarrow> fm" where
   373   "decr (Lt a) = Lt (decrnum a)"
   374 | "decr (Le a) = Le (decrnum a)"
   375 | "decr (Gt a) = Gt (decrnum a)"
   376 | "decr (Ge a) = Ge (decrnum a)"
   377 | "decr (Eq a) = Eq (decrnum a)"
   378 | "decr (NEq a) = NEq (decrnum a)"
   379 | "decr (Dvd i a) = Dvd i (decrnum a)"
   380 | "decr (NDvd i a) = NDvd i (decrnum a)"
   381 | "decr (NOT p) = NOT (decr p)" 
   382 | "decr (And p q) = And (decr p) (decr q)"
   383 | "decr (Or p q) = Or (decr p) (decr q)"
   384 | "decr (Imp p q) = Imp (decr p) (decr q)"
   385 | "decr (Iff p q) = Iff (decr p) (decr q)"
   386 | "decr p = p"
   387 
   388 lemma decrnum: assumes nb: "numbound0 t"
   389   shows "Inum (x#bs) t = Inum bs (decrnum t)"
   390   using nb by (induct t rule: decrnum.induct, simp_all)
   391 
   392 lemma decr: assumes nb: "bound0 p"
   393   shows "Ifm (x#bs) p = Ifm bs (decr p)"
   394   using nb 
   395   by (induct p rule: decr.induct, simp_all add: decrnum)
   396 
   397 lemma decr_qf: "bound0 p \<Longrightarrow> qfree (decr p)"
   398 by (induct p, simp_all)
   399 
   400 fun isatom :: "fm \<Rightarrow> bool" (* test for atomicity *) where
   401   "isatom T = True"
   402 | "isatom F = True"
   403 | "isatom (Lt a) = True"
   404 | "isatom (Le a) = True"
   405 | "isatom (Gt a) = True"
   406 | "isatom (Ge a) = True"
   407 | "isatom (Eq a) = True"
   408 | "isatom (NEq a) = True"
   409 | "isatom (Dvd i b) = True"
   410 | "isatom (NDvd i b) = True"
   411 | "isatom p = False"
   412 
   413 lemma numsubst0_numbound0: assumes nb: "numbound0 t"
   414   shows "numbound0 (numsubst0 t a)"
   415 using nb by (induct a, auto)
   416 
   417 lemma subst0_bound0: assumes qf: "qfree p" and nb: "numbound0 t"
   418   shows "bound0 (subst0 t p)"
   419 using qf numsubst0_numbound0[OF nb] by (induct p, auto)
   420 
   421 lemma bound0_qf: "bound0 p \<Longrightarrow> qfree p"
   422 by (induct p, simp_all)
   423 
   424 
   425 definition djf:: "('a \<Rightarrow> fm) \<Rightarrow> 'a \<Rightarrow> fm \<Rightarrow> fm" where
   426   "djf f p q = (if q=T then T else if q=F then f p else 
   427   (let fp = f p in case fp of T \<Rightarrow> T | F \<Rightarrow> q | _ \<Rightarrow> Or fp q))"
   428 
   429 definition evaldjf:: "('a \<Rightarrow> fm) \<Rightarrow> 'a list \<Rightarrow> fm" where
   430   "evaldjf f ps = foldr (djf f) ps F"
   431 
   432 lemma djf_Or: "Ifm bs (djf f p q) = Ifm bs (Or (f p) q)"
   433 by (cases "q=T", simp add: djf_def,cases "q=F",simp add: djf_def) 
   434 (cases "f p", simp_all add: Let_def djf_def) 
   435 
   436 lemma evaldjf_ex: "Ifm bs (evaldjf f ps) = (\<exists> p \<in> set ps. Ifm bs (f p))"
   437   by(induct ps, simp_all add: evaldjf_def djf_Or)
   438 
   439 lemma evaldjf_bound0: 
   440   assumes nb: "\<forall> x\<in> set xs. bound0 (f x)"
   441   shows "bound0 (evaldjf f xs)"
   442   using nb by (induct xs, auto simp add: evaldjf_def djf_def Let_def) (case_tac "f a", auto) 
   443 
   444 lemma evaldjf_qf: 
   445   assumes nb: "\<forall> x\<in> set xs. qfree (f x)"
   446   shows "qfree (evaldjf f xs)"
   447   using nb by (induct xs, auto simp add: evaldjf_def djf_def Let_def) (case_tac "f a", auto) 
   448 
   449 fun disjuncts :: "fm \<Rightarrow> fm list" where
   450   "disjuncts (Or p q) = (disjuncts p) @ (disjuncts q)"
   451 | "disjuncts F = []"
   452 | "disjuncts p = [p]"
   453 
   454 fun conjuncts :: "fm \<Rightarrow> fm list" where
   455   "conjuncts (And p q) = (conjuncts p) @ (conjuncts q)"
   456 | "conjuncts T = []"
   457 | "conjuncts p = [p]"
   458 
   459 lemma conjuncts: "(\<forall> q\<in> set (conjuncts p). Ifm bs q) = Ifm bs p"
   460 by(induct p rule: conjuncts.induct, auto)
   461 
   462 lemma disjuncts_qf: "qfree p \<Longrightarrow> \<forall> q\<in> set (disjuncts p). qfree q"
   463 proof-
   464   assume qf: "qfree p"
   465   hence "list_all qfree (disjuncts p)"
   466     by (induct p rule: disjuncts.induct, auto)
   467   thus ?thesis by (simp only: list_all_iff)
   468 qed
   469 lemma conjuncts_qf: "qfree p \<Longrightarrow> \<forall> q\<in> set (conjuncts p). qfree q"
   470 proof-
   471   assume qf: "qfree p"
   472   hence "list_all qfree (conjuncts p)"
   473     by (induct p rule: conjuncts.induct, auto)
   474   thus ?thesis by (simp only: list_all_iff)
   475 qed
   476 
   477 definition DJ :: "(fm \<Rightarrow> fm) \<Rightarrow> fm \<Rightarrow> fm" where
   478   "DJ f p \<equiv> evaldjf f (disjuncts p)"
   479 
   480 lemma DJ: assumes fdj: "\<forall> p q. f (Or p q) = Or (f p) (f q)"
   481   and fF: "f F = F"
   482   shows "Ifm bs (DJ f p) = Ifm bs (f p)"
   483 proof-
   484   have "Ifm bs (DJ f p) = (\<exists> q \<in> set (disjuncts p). Ifm bs (f q))"
   485     by (simp add: DJ_def evaldjf_ex) 
   486   also have "\<dots> = Ifm bs (f p)" using fdj fF by (induct p rule: disjuncts.induct, auto)
   487   finally show ?thesis .
   488 qed
   489 
   490 lemma DJ_qf: assumes 
   491   fqf: "\<forall> p. qfree p \<longrightarrow> qfree (f p)"
   492   shows "\<forall>p. qfree p \<longrightarrow> qfree (DJ f p) "
   493 proof(clarify)
   494   fix  p assume qf: "qfree p"
   495   have th: "DJ f p = evaldjf f (disjuncts p)" by (simp add: DJ_def)
   496   from disjuncts_qf[OF qf] have "\<forall> q\<in> set (disjuncts p). qfree q" .
   497   with fqf have th':"\<forall> q\<in> set (disjuncts p). qfree (f q)" by blast
   498   
   499   from evaldjf_qf[OF th'] th show "qfree (DJ f p)" by simp
   500 qed
   501 
   502 lemma DJ_qe: assumes qe: "\<forall> bs p. qfree p \<longrightarrow> qfree (qe p) \<and> (Ifm bs (qe p) = Ifm bs (E p))"
   503   shows "\<forall> bs p. qfree p \<longrightarrow> qfree (DJ qe p) \<and> (Ifm bs ((DJ qe p)) = Ifm bs (E p))"
   504 proof(clarify)
   505   fix p::fm and bs
   506   assume qf: "qfree p"
   507   from qe have qth: "\<forall> p. qfree p \<longrightarrow> qfree (qe p)" by blast
   508   from DJ_qf[OF qth] qf have qfth:"qfree (DJ qe p)" by auto
   509   have "Ifm bs (DJ qe p) = (\<exists> q\<in> set (disjuncts p). Ifm bs (qe q))"
   510     by (simp add: DJ_def evaldjf_ex)
   511   also have "\<dots> = (\<exists> q \<in> set(disjuncts p). Ifm bs (E q))" using qe disjuncts_qf[OF qf] by auto
   512   also have "\<dots> = Ifm bs (E p)" by (induct p rule: disjuncts.induct, auto)
   513   finally show "qfree (DJ qe p) \<and> Ifm bs (DJ qe p) = Ifm bs (E p)" using qfth by blast
   514 qed
   515   (* Simplification *)
   516 
   517   (* Algebraic simplifications for nums *)
   518 fun bnds:: "num \<Rightarrow> nat list" where
   519   "bnds (Bound n) = [n]"
   520 | "bnds (CN n c a) = n#(bnds a)"
   521 | "bnds (Neg a) = bnds a"
   522 | "bnds (Add a b) = (bnds a)@(bnds b)"
   523 | "bnds (Sub a b) = (bnds a)@(bnds b)"
   524 | "bnds (Mul i a) = bnds a"
   525 | "bnds (Floor a) = bnds a"
   526 | "bnds (CF c a b) = (bnds a)@(bnds b)"
   527 | "bnds a = []"
   528 fun lex_ns:: "nat list \<Rightarrow> nat list \<Rightarrow> bool" where
   529   "lex_ns [] ms = True"
   530 | "lex_ns ns [] = False"
   531 | "lex_ns (n#ns) (m#ms) = (n<m \<or> ((n = m) \<and> lex_ns ns ms)) "
   532 definition lex_bnd :: "num \<Rightarrow> num \<Rightarrow> bool" where
   533   "lex_bnd t s \<equiv> lex_ns (bnds t) (bnds s)"
   534 
   535 fun maxcoeff:: "num \<Rightarrow> int" where
   536   "maxcoeff (C i) = abs i"
   537 | "maxcoeff (CN n c t) = max (abs c) (maxcoeff t)"
   538 | "maxcoeff (CF c t s) = max (abs c) (maxcoeff s)"
   539 | "maxcoeff t = 1"
   540 
   541 lemma maxcoeff_pos: "maxcoeff t \<ge> 0"
   542   apply (induct t rule: maxcoeff.induct, auto) 
   543   done
   544 
   545 fun numgcdh:: "num \<Rightarrow> int \<Rightarrow> int" where
   546   "numgcdh (C i) = (\<lambda>g. gcd i g)"
   547 | "numgcdh (CN n c t) = (\<lambda>g. gcd c (numgcdh t g))"
   548 | "numgcdh (CF c s t) = (\<lambda>g. gcd c (numgcdh t g))"
   549 | "numgcdh t = (\<lambda>g. 1)"
   550 
   551 definition
   552   numgcd :: "num \<Rightarrow> int"
   553 where
   554   numgcd_def: "numgcd t = numgcdh t (maxcoeff t)"
   555 
   556 fun reducecoeffh:: "num \<Rightarrow> int \<Rightarrow> num" where
   557   "reducecoeffh (C i) = (\<lambda> g. C (i div g))"
   558 | "reducecoeffh (CN n c t) = (\<lambda> g. CN n (c div g) (reducecoeffh t g))"
   559 | "reducecoeffh (CF c s t) = (\<lambda> g. CF (c div g)  s (reducecoeffh t g))"
   560 | "reducecoeffh t = (\<lambda>g. t)"
   561 
   562 definition
   563   reducecoeff :: "num \<Rightarrow> num"
   564 where
   565   reducecoeff_def: "reducecoeff t =
   566   (let g = numgcd t in 
   567   if g = 0 then C 0 else if g=1 then t else reducecoeffh t g)"
   568 
   569 fun dvdnumcoeff:: "num \<Rightarrow> int \<Rightarrow> bool" where
   570   "dvdnumcoeff (C i) = (\<lambda> g. g dvd i)"
   571 | "dvdnumcoeff (CN n c t) = (\<lambda> g. g dvd c \<and> (dvdnumcoeff t g))"
   572 | "dvdnumcoeff (CF c s t) = (\<lambda> g. g dvd c \<and> (dvdnumcoeff t g))"
   573 | "dvdnumcoeff t = (\<lambda>g. False)"
   574 
   575 lemma dvdnumcoeff_trans: 
   576   assumes gdg: "g dvd g'" and dgt':"dvdnumcoeff t g'"
   577   shows "dvdnumcoeff t g"
   578   using dgt' gdg 
   579   by (induct t rule: dvdnumcoeff.induct, simp_all add: gdg dvd_trans[OF gdg])
   580 
   581 declare dvd_trans [trans add]
   582 
   583 lemma numgcd0:
   584   assumes g0: "numgcd t = 0"
   585   shows "Inum bs t = 0"
   586 proof-
   587   have "\<And>x. numgcdh t x= 0 \<Longrightarrow> Inum bs t = 0"
   588     by (induct t rule: numgcdh.induct, auto)
   589   thus ?thesis using g0[simplified numgcd_def] by blast
   590 qed
   591 
   592 lemma numgcdh_pos: assumes gp: "g \<ge> 0" shows "numgcdh t g \<ge> 0"
   593   using gp
   594   by (induct t rule: numgcdh.induct, auto)
   595 
   596 lemma numgcd_pos: "numgcd t \<ge>0"
   597   by (simp add: numgcd_def numgcdh_pos maxcoeff_pos)
   598 
   599 lemma reducecoeffh:
   600   assumes gt: "dvdnumcoeff t g" and gp: "g > 0" 
   601   shows "real g *(Inum bs (reducecoeffh t g)) = Inum bs t"
   602   using gt
   603 proof(induct t rule: reducecoeffh.induct) 
   604   case (1 i) hence gd: "g dvd i" by simp
   605   from assms 1 show ?case by (simp add: real_of_int_div[OF gd])
   606 next
   607   case (2 n c t)  hence gd: "g dvd c" by simp
   608   from assms 2 show ?case by (simp add: real_of_int_div[OF gd] algebra_simps)
   609 next
   610   case (3 c s t)  hence gd: "g dvd c" by simp
   611   from assms 3 show ?case by (simp add: real_of_int_div[OF gd] algebra_simps) 
   612 qed (auto simp add: numgcd_def gp)
   613 
   614 fun ismaxcoeff:: "num \<Rightarrow> int \<Rightarrow> bool" where
   615   "ismaxcoeff (C i) = (\<lambda> x. abs i \<le> x)"
   616 | "ismaxcoeff (CN n c t) = (\<lambda>x. abs c \<le> x \<and> (ismaxcoeff t x))"
   617 | "ismaxcoeff (CF c s t) = (\<lambda>x. abs c \<le> x \<and> (ismaxcoeff t x))"
   618 | "ismaxcoeff t = (\<lambda>x. True)"
   619 
   620 lemma ismaxcoeff_mono: "ismaxcoeff t c \<Longrightarrow> c \<le> c' \<Longrightarrow> ismaxcoeff t c'"
   621 by (induct t rule: ismaxcoeff.induct, auto)
   622 
   623 lemma maxcoeff_ismaxcoeff: "ismaxcoeff t (maxcoeff t)"
   624 proof (induct t rule: maxcoeff.induct)
   625   case (2 n c t)
   626   hence H:"ismaxcoeff t (maxcoeff t)" .
   627   have thh: "maxcoeff t \<le> max (abs c) (maxcoeff t)" by simp
   628   from ismaxcoeff_mono[OF H thh] show ?case by (simp add: le_maxI1)
   629 next
   630   case (3 c t s) 
   631   hence H1:"ismaxcoeff s (maxcoeff s)" by auto
   632   have thh1: "maxcoeff s \<le> max \<bar>c\<bar> (maxcoeff s)" by (simp add: max_def)
   633   from ismaxcoeff_mono[OF H1 thh1] show ?case by (simp add: le_maxI1)
   634 qed simp_all
   635 
   636 lemma zgcd_gt1: "gcd i j > (1::int) \<Longrightarrow> ((abs i > 1 \<and> abs j > 1) \<or> (abs i = 0 \<and> abs j > 1) \<or> (abs i > 1 \<and> abs j = 0))"
   637   apply (unfold gcd_int_def)
   638   apply (cases "i = 0", simp_all)
   639   apply (cases "j = 0", simp_all)
   640   apply (cases "abs i = 1", simp_all)
   641   apply (cases "abs j = 1", simp_all)
   642   apply auto
   643   done
   644 lemma numgcdh0:"numgcdh t m = 0 \<Longrightarrow>  m =0"
   645   by (induct t rule: numgcdh.induct) auto
   646 
   647 lemma dvdnumcoeff_aux:
   648   assumes "ismaxcoeff t m" and mp:"m \<ge> 0" and "numgcdh t m > 1"
   649   shows "dvdnumcoeff t (numgcdh t m)"
   650 using assms
   651 proof(induct t rule: numgcdh.induct)
   652   case (2 n c t) 
   653   let ?g = "numgcdh t m"
   654   from 2 have th:"gcd c ?g > 1" by simp
   655   from zgcd_gt1[OF th] numgcdh_pos[OF mp, where t="t"]
   656   have "(abs c > 1 \<and> ?g > 1) \<or> (abs c = 0 \<and> ?g > 1) \<or> (abs c > 1 \<and> ?g = 0)" by simp
   657   moreover {assume "abs c > 1" and gp: "?g > 1" with 2
   658     have th: "dvdnumcoeff t ?g" by simp
   659     have th': "gcd c ?g dvd ?g" by simp
   660     from dvdnumcoeff_trans[OF th' th] have ?case by simp }
   661   moreover {assume "abs c = 0 \<and> ?g > 1"
   662     with 2 have th: "dvdnumcoeff t ?g" by simp
   663     have th': "gcd c ?g dvd ?g" by simp
   664     from dvdnumcoeff_trans[OF th' th] have ?case by simp
   665     hence ?case by simp }
   666   moreover {assume "abs c > 1" and g0:"?g = 0" 
   667     from numgcdh0[OF g0] have "m=0". with 2 g0 have ?case by simp }
   668   ultimately show ?case by blast
   669 next
   670   case (3 c s t) 
   671   let ?g = "numgcdh t m"
   672   from 3 have th:"gcd c ?g > 1" by simp
   673   from zgcd_gt1[OF th] numgcdh_pos[OF mp, where t="t"]
   674   have "(abs c > 1 \<and> ?g > 1) \<or> (abs c = 0 \<and> ?g > 1) \<or> (abs c > 1 \<and> ?g = 0)" by simp
   675   moreover {assume "abs c > 1" and gp: "?g > 1" with 3
   676     have th: "dvdnumcoeff t ?g" by simp
   677     have th': "gcd c ?g dvd ?g" by simp
   678     from dvdnumcoeff_trans[OF th' th] have ?case by simp }
   679   moreover {assume "abs c = 0 \<and> ?g > 1"
   680     with 3 have th: "dvdnumcoeff t ?g" by simp
   681     have th': "gcd c ?g dvd ?g" by simp
   682     from dvdnumcoeff_trans[OF th' th] have ?case by simp
   683     hence ?case by simp }
   684   moreover {assume "abs c > 1" and g0:"?g = 0" 
   685     from numgcdh0[OF g0] have "m=0". with 3 g0 have ?case by simp }
   686   ultimately show ?case by blast
   687 qed auto
   688 
   689 lemma dvdnumcoeff_aux2:
   690   assumes "numgcd t > 1" shows "dvdnumcoeff t (numgcd t) \<and> numgcd t > 0"
   691   using assms 
   692 proof (simp add: numgcd_def)
   693   let ?mc = "maxcoeff t"
   694   let ?g = "numgcdh t ?mc"
   695   have th1: "ismaxcoeff t ?mc" by (rule maxcoeff_ismaxcoeff)
   696   have th2: "?mc \<ge> 0" by (rule maxcoeff_pos)
   697   assume H: "numgcdh t ?mc > 1"
   698   from dvdnumcoeff_aux[OF th1 th2 H] show "dvdnumcoeff t ?g" .
   699 qed
   700 
   701 lemma reducecoeff: "real (numgcd t) * (Inum bs (reducecoeff t)) = Inum bs t"
   702 proof-
   703   let ?g = "numgcd t"
   704   have "?g \<ge> 0"  by (simp add: numgcd_pos)
   705   hence "?g = 0 \<or> ?g = 1 \<or> ?g > 1" by auto
   706   moreover {assume "?g = 0" hence ?thesis by (simp add: numgcd0)} 
   707   moreover {assume "?g = 1" hence ?thesis by (simp add: reducecoeff_def)} 
   708   moreover { assume g1:"?g > 1"
   709     from dvdnumcoeff_aux2[OF g1] have th1:"dvdnumcoeff t ?g" and g0: "?g > 0" by blast+
   710     from reducecoeffh[OF th1 g0, where bs="bs"] g1 have ?thesis 
   711       by (simp add: reducecoeff_def Let_def)} 
   712   ultimately show ?thesis by blast
   713 qed
   714 
   715 lemma reducecoeffh_numbound0: "numbound0 t \<Longrightarrow> numbound0 (reducecoeffh t g)"
   716 by (induct t rule: reducecoeffh.induct, auto)
   717 
   718 lemma reducecoeff_numbound0: "numbound0 t \<Longrightarrow> numbound0 (reducecoeff t)"
   719 using reducecoeffh_numbound0 by (simp add: reducecoeff_def Let_def)
   720 
   721 consts
   722   numadd:: "num \<times> num \<Rightarrow> num"
   723 
   724 recdef numadd "measure (\<lambda> (t,s). size t + size s)"
   725   "numadd (CN n1 c1 r1,CN n2 c2 r2) =
   726   (if n1=n2 then 
   727   (let c = c1 + c2
   728   in (if c=0 then numadd(r1,r2) else CN n1 c (numadd (r1,r2))))
   729   else if n1 \<le> n2 then CN n1 c1 (numadd (r1,CN n2 c2 r2))
   730   else (CN n2 c2 (numadd (CN n1 c1 r1,r2))))"
   731   "numadd (CN n1 c1 r1,t) = CN n1 c1 (numadd (r1, t))"  
   732   "numadd (t,CN n2 c2 r2) = CN n2 c2 (numadd (t,r2))" 
   733   "numadd (CF c1 t1 r1,CF c2 t2 r2) = 
   734    (if t1 = t2 then 
   735     (let c=c1+c2; s= numadd(r1,r2) in (if c=0 then s else CF c t1 s))
   736    else if lex_bnd t1 t2 then CF c1 t1 (numadd(r1,CF c2 t2 r2))
   737    else CF c2 t2 (numadd(CF c1 t1 r1,r2)))"
   738   "numadd (CF c1 t1 r1,C c) = CF c1 t1 (numadd (r1, C c))"
   739   "numadd (C c,CF c1 t1 r1) = CF c1 t1 (numadd (r1, C c))"
   740   "numadd (C b1, C b2) = C (b1+b2)"
   741   "numadd (a,b) = Add a b"
   742 
   743 lemma numadd[simp]: "Inum bs (numadd (t,s)) = Inum bs (Add t s)"
   744 apply (induct t s rule: numadd.induct, simp_all add: Let_def)
   745  apply (case_tac "c1+c2 = 0",case_tac "n1 \<le> n2", simp_all)
   746   apply (case_tac "n1 = n2", simp_all add: algebra_simps)
   747   apply (simp only: left_distrib[symmetric])
   748  apply simp
   749 apply (case_tac "lex_bnd t1 t2", simp_all)
   750  apply (case_tac "c1+c2 = 0")
   751   by (case_tac "t1 = t2", simp_all add: algebra_simps left_distrib[symmetric] real_of_int_mult[symmetric] real_of_int_add[symmetric]del: real_of_int_mult real_of_int_add left_distrib)
   752 
   753 lemma numadd_nb[simp]: "\<lbrakk> numbound0 t ; numbound0 s\<rbrakk> \<Longrightarrow> numbound0 (numadd (t,s))"
   754 by (induct t s rule: numadd.induct, auto simp add: Let_def)
   755 
   756 fun nummul:: "num \<Rightarrow> int \<Rightarrow> num" where
   757   "nummul (C j) = (\<lambda> i. C (i*j))"
   758 | "nummul (CN n c t) = (\<lambda> i. CN n (c*i) (nummul t i))"
   759 | "nummul (CF c t s) = (\<lambda> i. CF (c*i) t (nummul s i))"
   760 | "nummul (Mul c t) = (\<lambda> i. nummul t (i*c))"
   761 | "nummul t = (\<lambda> i. Mul i t)"
   762 
   763 lemma nummul[simp]: "\<And> i. Inum bs (nummul t i) = Inum bs (Mul i t)"
   764 by (induct t rule: nummul.induct, auto simp add: algebra_simps)
   765 
   766 lemma nummul_nb[simp]: "\<And> i. numbound0 t \<Longrightarrow> numbound0 (nummul t i)"
   767 by (induct t rule: nummul.induct, auto)
   768 
   769 definition numneg :: "num \<Rightarrow> num" where
   770   "numneg t \<equiv> nummul t (- 1)"
   771 
   772 definition numsub :: "num \<Rightarrow> num \<Rightarrow> num" where
   773   "numsub s t \<equiv> (if s = t then C 0 else numadd (s,numneg t))"
   774 
   775 lemma numneg[simp]: "Inum bs (numneg t) = Inum bs (Neg t)"
   776 using numneg_def nummul by simp
   777 
   778 lemma numneg_nb[simp]: "numbound0 t \<Longrightarrow> numbound0 (numneg t)"
   779 using numneg_def by simp
   780 
   781 lemma numsub[simp]: "Inum bs (numsub a b) = Inum bs (Sub a b)"
   782 using numsub_def by simp
   783 
   784 lemma numsub_nb[simp]: "\<lbrakk> numbound0 t ; numbound0 s\<rbrakk> \<Longrightarrow> numbound0 (numsub t s)"
   785 using numsub_def by simp
   786 
   787 lemma isint_CF: assumes si: "isint s bs" shows "isint (CF c t s) bs"
   788 proof-
   789   have cti: "isint (Mul c (Floor t)) bs" by (simp add: isint_Mul isint_Floor)
   790   
   791   have "?thesis = isint (Add (Mul c (Floor t)) s) bs" by (simp add: isint_def)
   792   also have "\<dots>" by (simp add: isint_add cti si)
   793   finally show ?thesis .
   794 qed
   795 
   796 fun split_int:: "num \<Rightarrow> num \<times> num" where
   797   "split_int (C c) = (C 0, C c)"
   798 | "split_int (CN n c b) = 
   799      (let (bv,bi) = split_int b 
   800        in (CN n c bv, bi))"
   801 | "split_int (CF c a b) = 
   802      (let (bv,bi) = split_int b 
   803        in (bv, CF c a bi))"
   804 | "split_int a = (a,C 0)"
   805 
   806 lemma split_int: "\<And>tv ti. split_int t = (tv,ti) \<Longrightarrow> (Inum bs (Add tv ti) = Inum bs t) \<and> isint ti bs"
   807 proof (induct t rule: split_int.induct)
   808   case (2 c n b tv ti)
   809   let ?bv = "fst (split_int b)"
   810   let ?bi = "snd (split_int b)"
   811   have "split_int b = (?bv,?bi)" by simp
   812   with 2(1) have b:"Inum bs (Add ?bv ?bi) = Inum bs b" and bii: "isint ?bi bs" by blast+
   813   from 2(2) have tibi: "ti = ?bi" by (simp add: Let_def split_def)
   814   from 2(2) b[symmetric] bii show ?case by (auto simp add: Let_def split_def)
   815 next
   816   case (3 c a b tv ti) 
   817   let ?bv = "fst (split_int b)"
   818   let ?bi = "snd (split_int b)"
   819   have "split_int b = (?bv,?bi)" by simp
   820   with 3(1) have b:"Inum bs (Add ?bv ?bi) = Inum bs b" and bii: "isint ?bi bs" by blast+
   821   from 3(2) have tibi: "ti = CF c a ?bi"
   822     by (simp add: Let_def split_def)
   823   from 3(2) b[symmetric] bii show ?case
   824     by (auto simp add: Let_def split_def isint_Floor isint_add isint_Mul isint_CF)
   825 qed (auto simp add: Let_def isint_iff isint_Floor isint_add isint_Mul split_def algebra_simps)
   826 
   827 lemma split_int_nb: "numbound0 t \<Longrightarrow> numbound0 (fst (split_int t)) \<and> numbound0 (snd (split_int t)) "
   828   by (induct t rule: split_int.induct) (auto simp add: Let_def split_def)
   829 
   830 definition numfloor:: "num \<Rightarrow> num"
   831 where
   832   "numfloor t = (let (tv,ti) = split_int t in 
   833   (case tv of C i \<Rightarrow> numadd (tv,ti) 
   834   | _ \<Rightarrow> numadd(CF 1 tv (C 0),ti)))"
   835 
   836 lemma numfloor[simp]: "Inum bs (numfloor t) = Inum bs (Floor t)" (is "?n t = ?N (Floor t)")
   837 proof-
   838   let ?tv = "fst (split_int t)"
   839   let ?ti = "snd (split_int t)"
   840   have tvti:"split_int t = (?tv,?ti)" by simp
   841   {assume H: "\<forall> v. ?tv \<noteq> C v"
   842     hence th1: "?n t = ?N (Add (Floor ?tv) ?ti)" 
   843       by (cases ?tv, auto simp add: numfloor_def Let_def split_def numadd)
   844     from split_int[OF tvti] have "?N (Floor t) = ?N (Floor(Add ?tv ?ti))" and tii:"isint ?ti bs" by simp+
   845     hence "?N (Floor t) = real (floor (?N (Add ?tv ?ti)))" by simp 
   846     also have "\<dots> = real (floor (?N ?tv) + (floor (?N ?ti)))"
   847       by (simp,subst tii[simplified isint_iff, symmetric]) simp
   848     also have "\<dots> = ?N (Add (Floor ?tv) ?ti)" by (simp add: tii[simplified isint_iff])
   849     finally have ?thesis using th1 by simp}
   850   moreover {fix v assume H:"?tv = C v" 
   851     from split_int[OF tvti] have "?N (Floor t) = ?N (Floor(Add ?tv ?ti))" and tii:"isint ?ti bs" by simp+
   852     hence "?N (Floor t) = real (floor (?N (Add ?tv ?ti)))" by simp 
   853     also have "\<dots> = real (floor (?N ?tv) + (floor (?N ?ti)))"
   854       by (simp,subst tii[simplified isint_iff, symmetric]) simp
   855     also have "\<dots> = ?N (Add (Floor ?tv) ?ti)" by (simp add: tii[simplified isint_iff])
   856     finally have ?thesis by (simp add: H numfloor_def Let_def split_def numadd) }
   857   ultimately show ?thesis by auto
   858 qed
   859 
   860 lemma numfloor_nb[simp]: "numbound0 t \<Longrightarrow> numbound0 (numfloor t)"
   861   using split_int_nb[where t="t"]
   862   by (cases "fst(split_int t)" , auto simp add: numfloor_def Let_def split_def  numadd_nb)
   863 
   864 function simpnum:: "num \<Rightarrow> num" where
   865   "simpnum (C j) = C j"
   866 | "simpnum (Bound n) = CN n 1 (C 0)"
   867 | "simpnum (Neg t) = numneg (simpnum t)"
   868 | "simpnum (Add t s) = numadd (simpnum t,simpnum s)"
   869 | "simpnum (Sub t s) = numsub (simpnum t) (simpnum s)"
   870 | "simpnum (Mul i t) = (if i = 0 then (C 0) else nummul (simpnum t) i)"
   871 | "simpnum (Floor t) = numfloor (simpnum t)"
   872 | "simpnum (CN n c t) = (if c=0 then simpnum t else CN n c (simpnum t))"
   873 | "simpnum (CF c t s) = simpnum(Add (Mul c (Floor t)) s)"
   874 by pat_completeness auto
   875 termination by (relation "measure num_size") auto
   876 
   877 lemma simpnum_ci[simp]: "Inum bs (simpnum t) = Inum bs t"
   878 by (induct t rule: simpnum.induct, auto)
   879 
   880 lemma simpnum_numbound0[simp]: 
   881   "numbound0 t \<Longrightarrow> numbound0 (simpnum t)"
   882 by (induct t rule: simpnum.induct, auto)
   883 
   884 fun nozerocoeff:: "num \<Rightarrow> bool" where
   885   "nozerocoeff (C c) = True"
   886 | "nozerocoeff (CN n c t) = (c\<noteq>0 \<and> nozerocoeff t)"
   887 | "nozerocoeff (CF c s t) = (c \<noteq> 0 \<and> nozerocoeff t)"
   888 | "nozerocoeff (Mul c t) = (c\<noteq>0 \<and> nozerocoeff t)"
   889 | "nozerocoeff t = True"
   890 
   891 lemma numadd_nz : "nozerocoeff a \<Longrightarrow> nozerocoeff b \<Longrightarrow> nozerocoeff (numadd (a,b))"
   892 by (induct a b rule: numadd.induct,auto simp add: Let_def)
   893 
   894 lemma nummul_nz : "\<And> i. i\<noteq>0 \<Longrightarrow> nozerocoeff a \<Longrightarrow> nozerocoeff (nummul a i)"
   895   by (induct a rule: nummul.induct,auto simp add: Let_def numadd_nz)
   896 
   897 lemma numneg_nz : "nozerocoeff a \<Longrightarrow> nozerocoeff (numneg a)"
   898 by (simp add: numneg_def nummul_nz)
   899 
   900 lemma numsub_nz: "nozerocoeff a \<Longrightarrow> nozerocoeff b \<Longrightarrow> nozerocoeff (numsub a b)"
   901 by (simp add: numsub_def numneg_nz numadd_nz)
   902 
   903 lemma split_int_nz: "nozerocoeff t \<Longrightarrow> nozerocoeff (fst (split_int t)) \<and> nozerocoeff (snd (split_int t))"
   904 by (induct t rule: split_int.induct,auto simp add: Let_def split_def)
   905 
   906 lemma numfloor_nz: "nozerocoeff t \<Longrightarrow> nozerocoeff (numfloor t)"
   907 by (simp add: numfloor_def Let_def split_def)
   908 (cases "fst (split_int t)", simp_all add: split_int_nz numadd_nz)
   909 
   910 lemma simpnum_nz: "nozerocoeff (simpnum t)"
   911 by(induct t rule: simpnum.induct, auto simp add: numadd_nz numneg_nz numsub_nz nummul_nz numfloor_nz)
   912 
   913 lemma maxcoeff_nz: "nozerocoeff t \<Longrightarrow> maxcoeff t = 0 \<Longrightarrow> t = C 0"
   914 proof (induct t rule: maxcoeff.induct)
   915   case (2 n c t)
   916   hence cnz: "c \<noteq>0" and mx: "max (abs c) (maxcoeff t) = 0" by simp+
   917   have "max (abs c) (maxcoeff t) \<ge> abs c" by (simp add: le_maxI1)
   918   with cnz have "max (abs c) (maxcoeff t) > 0" by arith
   919   with 2 show ?case by simp
   920 next
   921   case (3 c s t) 
   922   hence cnz: "c \<noteq>0" and mx: "max (abs c) (maxcoeff t) = 0" by simp+
   923   have "max (abs c) (maxcoeff t) \<ge> abs c" by (simp add: le_maxI1)
   924   with cnz have "max (abs c) (maxcoeff t) > 0" by arith
   925   with 3 show ?case by simp
   926 qed auto
   927 
   928 lemma numgcd_nz: assumes nz: "nozerocoeff t" and g0: "numgcd t = 0" shows "t = C 0"
   929 proof-
   930   from g0 have th:"numgcdh t (maxcoeff t) = 0" by (simp add: numgcd_def)
   931   from numgcdh0[OF th]  have th:"maxcoeff t = 0" .
   932   from maxcoeff_nz[OF nz th] show ?thesis .
   933 qed
   934 
   935 definition simp_num_pair :: "(num \<times> int) \<Rightarrow> num \<times> int" where
   936   "simp_num_pair \<equiv> (\<lambda> (t,n). (if n = 0 then (C 0, 0) else
   937    (let t' = simpnum t ; g = numgcd t' in 
   938       if g > 1 then (let g' = gcd n g in 
   939         if g' = 1 then (t',n) 
   940         else (reducecoeffh t' g', n div g')) 
   941       else (t',n))))"
   942 
   943 lemma simp_num_pair_ci:
   944   shows "((\<lambda> (t,n). Inum bs t / real n) (simp_num_pair (t,n))) = ((\<lambda> (t,n). Inum bs t / real n) (t,n))"
   945   (is "?lhs = ?rhs")
   946 proof-
   947   let ?t' = "simpnum t"
   948   let ?g = "numgcd ?t'"
   949   let ?g' = "gcd n ?g"
   950   {assume nz: "n = 0" hence ?thesis by (simp add: Let_def simp_num_pair_def)}
   951   moreover
   952   { assume nnz: "n \<noteq> 0"
   953     {assume "\<not> ?g > 1" hence ?thesis by (simp add: Let_def simp_num_pair_def)}
   954     moreover
   955     {assume g1:"?g>1" hence g0: "?g > 0" by simp
   956       from g1 nnz have gp0: "?g' \<noteq> 0" by simp
   957       hence g'p: "?g' > 0" using gcd_ge_0_int[where x="n" and y="numgcd ?t'"] by arith
   958       hence "?g'= 1 \<or> ?g' > 1" by arith
   959       moreover {assume "?g'=1" hence ?thesis by (simp add: Let_def simp_num_pair_def)}
   960       moreover {assume g'1:"?g'>1"
   961         from dvdnumcoeff_aux2[OF g1] have th1:"dvdnumcoeff ?t' ?g" ..
   962         let ?tt = "reducecoeffh ?t' ?g'"
   963         let ?t = "Inum bs ?tt"
   964         have gpdg: "?g' dvd ?g" by simp
   965         have gpdd: "?g' dvd n" by simp
   966         have gpdgp: "?g' dvd ?g'" by simp
   967         from reducecoeffh[OF dvdnumcoeff_trans[OF gpdg th1] g'p] 
   968         have th2:"real ?g' * ?t = Inum bs ?t'" by simp
   969         from nnz g1 g'1 have "?lhs = ?t / real (n div ?g')" by (simp add: simp_num_pair_def Let_def)
   970         also have "\<dots> = (real ?g' * ?t) / (real ?g' * (real (n div ?g')))" by simp
   971         also have "\<dots> = (Inum bs ?t' / real n)"
   972           using real_of_int_div[OF gpdd] th2 gp0 by simp
   973         finally have "?lhs = Inum bs t / real n" by simp
   974         then have ?thesis using nnz g1 g'1 by (simp add: simp_num_pair_def) }
   975       ultimately have ?thesis by blast }
   976     ultimately have ?thesis by blast }
   977   ultimately show ?thesis by blast
   978 qed
   979 
   980 lemma simp_num_pair_l:
   981   assumes tnb: "numbound0 t" and np: "n >0" and tn: "simp_num_pair (t,n) = (t',n')"
   982   shows "numbound0 t' \<and> n' >0"
   983 proof-
   984   let ?t' = "simpnum t"
   985   let ?g = "numgcd ?t'"
   986   let ?g' = "gcd n ?g"
   987   { assume nz: "n = 0" hence ?thesis using assms by (simp add: Let_def simp_num_pair_def) }
   988   moreover
   989   { assume nnz: "n \<noteq> 0"
   990     {assume "\<not> ?g > 1" hence ?thesis using assms by (auto simp add: Let_def simp_num_pair_def) }
   991     moreover
   992     {assume g1:"?g>1" hence g0: "?g > 0" by simp
   993       from g1 nnz have gp0: "?g' \<noteq> 0" by simp
   994       hence g'p: "?g' > 0" using gcd_ge_0_int[where x="n" and y="numgcd ?t'"] by arith
   995       hence "?g'= 1 \<or> ?g' > 1" by arith
   996       moreover {assume "?g'=1" hence ?thesis using assms g1 g0
   997           by (auto simp add: Let_def simp_num_pair_def) }
   998       moreover {assume g'1:"?g'>1"
   999         have gpdg: "?g' dvd ?g" by simp
  1000         have gpdd: "?g' dvd n" by simp
  1001         have gpdgp: "?g' dvd ?g'" by simp
  1002         from zdvd_imp_le[OF gpdd np] have g'n: "?g' \<le> n" .
  1003         from zdiv_mono1[OF g'n g'p, simplified div_self[OF gp0]]
  1004         have "n div ?g' >0" by simp
  1005         hence ?thesis using assms g1 g'1
  1006           by(auto simp add: simp_num_pair_def Let_def reducecoeffh_numbound0)}
  1007       ultimately have ?thesis by blast }
  1008     ultimately have ?thesis by blast } 
  1009   ultimately show ?thesis by blast
  1010 qed
  1011 
  1012 fun not:: "fm \<Rightarrow> fm" where
  1013   "not (NOT p) = p"
  1014 | "not T = F"
  1015 | "not F = T"
  1016 | "not (Lt t) = Ge t"
  1017 | "not (Le t) = Gt t"
  1018 | "not (Gt t) = Le t"
  1019 | "not (Ge t) = Lt t"
  1020 | "not (Eq t) = NEq t"
  1021 | "not (NEq t) = Eq t"
  1022 | "not (Dvd i t) = NDvd i t"
  1023 | "not (NDvd i t) = Dvd i t"
  1024 | "not (And p q) = Or (not p) (not q)"
  1025 | "not (Or p q) = And (not p) (not q)"
  1026 | "not p = NOT p"
  1027 lemma not[simp]: "Ifm bs (not p) = Ifm bs (NOT p)"
  1028   by (induct p) auto
  1029 lemma not_qf[simp]: "qfree p \<Longrightarrow> qfree (not p)"
  1030   by (induct p) auto
  1031 lemma not_nb[simp]: "bound0 p \<Longrightarrow> bound0 (not p)"
  1032   by (induct p) auto
  1033 
  1034 definition conj :: "fm \<Rightarrow> fm \<Rightarrow> fm" where
  1035   "conj p q \<equiv> (if (p = F \<or> q=F) then F else if p=T then q else if q=T then p else 
  1036    if p = q then p else And p q)"
  1037 lemma conj[simp]: "Ifm bs (conj p q) = Ifm bs (And p q)"
  1038   by (cases "p=F \<or> q=F", simp_all add: conj_def) (cases p, simp_all)
  1039 
  1040 lemma conj_qf[simp]: "\<lbrakk>qfree p ; qfree q\<rbrakk> \<Longrightarrow> qfree (conj p q)"
  1041   using conj_def by auto 
  1042 lemma conj_nb[simp]: "\<lbrakk>bound0 p ; bound0 q\<rbrakk> \<Longrightarrow> bound0 (conj p q)"
  1043   using conj_def by auto 
  1044 
  1045 definition disj :: "fm \<Rightarrow> fm \<Rightarrow> fm" where
  1046   "disj p q \<equiv> (if (p = T \<or> q=T) then T else if p=F then q else if q=F then p 
  1047        else if p=q then p else Or p q)"
  1048 
  1049 lemma disj[simp]: "Ifm bs (disj p q) = Ifm bs (Or p q)"
  1050   by (cases "p=T \<or> q=T",simp_all add: disj_def) (cases p,simp_all)
  1051 lemma disj_qf[simp]: "\<lbrakk>qfree p ; qfree q\<rbrakk> \<Longrightarrow> qfree (disj p q)"
  1052   using disj_def by auto 
  1053 lemma disj_nb[simp]: "\<lbrakk>bound0 p ; bound0 q\<rbrakk> \<Longrightarrow> bound0 (disj p q)"
  1054   using disj_def by auto 
  1055 
  1056 definition imp :: "fm \<Rightarrow> fm \<Rightarrow> fm" where
  1057   "imp p q \<equiv> (if (p = F \<or> q=T \<or> p=q) then T else if p=T then q else if q=F then not p 
  1058     else Imp p q)"
  1059 lemma imp[simp]: "Ifm bs (imp p q) = Ifm bs (Imp p q)"
  1060   by (cases "p=F \<or> q=T",simp_all add: imp_def)
  1061 lemma imp_qf[simp]: "\<lbrakk>qfree p ; qfree q\<rbrakk> \<Longrightarrow> qfree (imp p q)"
  1062   using imp_def by (cases "p=F \<or> q=T",simp_all add: imp_def)
  1063 
  1064 definition iff :: "fm \<Rightarrow> fm \<Rightarrow> fm" where
  1065   "iff p q \<equiv> (if (p = q) then T else if (p = not q \<or> not p = q) then F else 
  1066        if p=F then not q else if q=F then not p else if p=T then q else if q=T then p else 
  1067   Iff p q)"
  1068 lemma iff[simp]: "Ifm bs (iff p q) = Ifm bs (Iff p q)"
  1069   by (unfold iff_def,cases "p=q", simp,cases "p=not q", simp add:not) 
  1070 (cases "not p= q", auto simp add:not)
  1071 lemma iff_qf[simp]: "\<lbrakk>qfree p ; qfree q\<rbrakk> \<Longrightarrow> qfree (iff p q)"
  1072   by (unfold iff_def,cases "p=q", auto)
  1073 
  1074 fun check_int:: "num \<Rightarrow> bool" where
  1075   "check_int (C i) = True"
  1076 | "check_int (Floor t) = True"
  1077 | "check_int (Mul i t) = check_int t"
  1078 | "check_int (Add t s) = (check_int t \<and> check_int s)"
  1079 | "check_int (Neg t) = check_int t"
  1080 | "check_int (CF c t s) = check_int s"
  1081 | "check_int t = False"
  1082 lemma check_int: "check_int t \<Longrightarrow> isint t bs"
  1083 by (induct t, auto simp add: isint_add isint_Floor isint_Mul isint_neg isint_c isint_CF)
  1084 
  1085 lemma rdvd_left1_int: "real \<lfloor>t\<rfloor> = t \<Longrightarrow> 1 rdvd t"
  1086   by (simp add: rdvd_def,rule_tac x="\<lfloor>t\<rfloor>" in exI) simp
  1087 
  1088 lemma rdvd_reduce: 
  1089   assumes gd:"g dvd d" and gc:"g dvd c" and gp: "g > 0"
  1090   shows "real (d::int) rdvd real (c::int)*t = (real (d div g) rdvd real (c div g)*t)"
  1091 proof
  1092   assume d: "real d rdvd real c * t"
  1093   from d rdvd_def obtain k where k_def: "real c * t = real d* real (k::int)" by auto
  1094   from gd dvd_def obtain kd where kd_def: "d = g * kd" by auto
  1095   from gc dvd_def obtain kc where kc_def: "c = g * kc" by auto
  1096   from k_def kd_def kc_def have "real g * real kc * t = real g * real kd * real k" by simp
  1097   hence "real kc * t = real kd * real k" using gp by simp
  1098   hence th:"real kd rdvd real kc * t" using rdvd_def by blast
  1099   from kd_def gp have th':"kd = d div g" by simp
  1100   from kc_def gp have "kc = c div g" by simp
  1101   with th th' show "real (d div g) rdvd real (c div g) * t" by simp
  1102 next
  1103   assume d: "real (d div g) rdvd real (c div g) * t"
  1104   from gp have gnz: "g \<noteq> 0" by simp
  1105   thus "real d rdvd real c * t" using d rdvd_mult[OF gnz, where n="d div g" and x="real (c div g) * t"] real_of_int_div[OF gd] real_of_int_div[OF gc] by simp
  1106 qed
  1107 
  1108 definition simpdvd :: "int \<Rightarrow> num \<Rightarrow> (int \<times> num)" where
  1109   "simpdvd d t \<equiv> 
  1110    (let g = numgcd t in 
  1111       if g > 1 then (let g' = gcd d g in 
  1112         if g' = 1 then (d, t) 
  1113         else (d div g',reducecoeffh t g')) 
  1114       else (d, t))"
  1115 lemma simpdvd: 
  1116   assumes tnz: "nozerocoeff t" and dnz: "d \<noteq> 0"
  1117   shows "Ifm bs (Dvd (fst (simpdvd d t)) (snd (simpdvd d t))) = Ifm bs (Dvd d t)"
  1118 proof-
  1119   let ?g = "numgcd t"
  1120   let ?g' = "gcd d ?g"
  1121   {assume "\<not> ?g > 1" hence ?thesis by (simp add: Let_def simpdvd_def)}
  1122   moreover
  1123   {assume g1:"?g>1" hence g0: "?g > 0" by simp
  1124     from g1 dnz have gp0: "?g' \<noteq> 0" by simp
  1125     hence g'p: "?g' > 0" using gcd_ge_0_int[where x="d" and y="numgcd t"] by arith
  1126     hence "?g'= 1 \<or> ?g' > 1" by arith
  1127     moreover {assume "?g'=1" hence ?thesis by (simp add: Let_def simpdvd_def)}
  1128     moreover {assume g'1:"?g'>1"
  1129       from dvdnumcoeff_aux2[OF g1] have th1:"dvdnumcoeff t ?g" ..
  1130       let ?tt = "reducecoeffh t ?g'"
  1131       let ?t = "Inum bs ?tt"
  1132       have gpdg: "?g' dvd ?g" by simp
  1133       have gpdd: "?g' dvd d" by simp
  1134       have gpdgp: "?g' dvd ?g'" by simp
  1135       from reducecoeffh[OF dvdnumcoeff_trans[OF gpdg th1] g'p] 
  1136       have th2:"real ?g' * ?t = Inum bs t" by simp
  1137       from assms g1 g0 g'1
  1138       have "Ifm bs (Dvd (fst (simpdvd d t)) (snd(simpdvd d t))) = Ifm bs (Dvd (d div ?g') ?tt)"
  1139         by (simp add: simpdvd_def Let_def)
  1140       also have "\<dots> = (real d rdvd (Inum bs t))"
  1141         using rdvd_reduce[OF gpdd gpdgp g'p, where t="?t", simplified div_self[OF gp0]] 
  1142           th2[symmetric] by simp
  1143       finally have ?thesis by simp  }
  1144     ultimately have ?thesis by blast
  1145   }
  1146   ultimately show ?thesis by blast
  1147 qed
  1148 
  1149 function (sequential) simpfm :: "fm \<Rightarrow> fm" where
  1150   "simpfm (And p q) = conj (simpfm p) (simpfm q)"
  1151 | "simpfm (Or p q) = disj (simpfm p) (simpfm q)"
  1152 | "simpfm (Imp p q) = imp (simpfm p) (simpfm q)"
  1153 | "simpfm (Iff p q) = iff (simpfm p) (simpfm q)"
  1154 | "simpfm (NOT p) = not (simpfm p)"
  1155 | "simpfm (Lt a) = (let a' = simpnum a in case a' of C v \<Rightarrow> if (v < 0) then T else F 
  1156   | _ \<Rightarrow> Lt (reducecoeff a'))"
  1157 | "simpfm (Le a) = (let a' = simpnum a in case a' of C v \<Rightarrow> if (v \<le> 0)  then T else F | _ \<Rightarrow> Le (reducecoeff a'))"
  1158 | "simpfm (Gt a) = (let a' = simpnum a in case a' of C v \<Rightarrow> if (v > 0)  then T else F | _ \<Rightarrow> Gt (reducecoeff a'))"
  1159 | "simpfm (Ge a) = (let a' = simpnum a in case a' of C v \<Rightarrow> if (v \<ge> 0)  then T else F | _ \<Rightarrow> Ge (reducecoeff a'))"
  1160 | "simpfm (Eq a) = (let a' = simpnum a in case a' of C v \<Rightarrow> if (v = 0)  then T else F | _ \<Rightarrow> Eq (reducecoeff a'))"
  1161 | "simpfm (NEq a) = (let a' = simpnum a in case a' of C v \<Rightarrow> if (v \<noteq> 0)  then T else F | _ \<Rightarrow> NEq (reducecoeff a'))"
  1162 | "simpfm (Dvd i a) = (if i=0 then simpfm (Eq a)
  1163              else if (abs i = 1) \<and> check_int a then T
  1164              else let a' = simpnum a in case a' of C v \<Rightarrow> if (i dvd v)  then T else F | _ \<Rightarrow> (let (d,t) = simpdvd i a' in Dvd d t))"
  1165 | "simpfm (NDvd i a) = (if i=0 then simpfm (NEq a) 
  1166              else if (abs i = 1) \<and> check_int a then F
  1167              else let a' = simpnum a in case a' of C v \<Rightarrow> if (\<not>(i dvd v)) then T else F | _ \<Rightarrow> (let (d,t) = simpdvd i a' in NDvd d t))"
  1168 | "simpfm p = p"
  1169 by pat_completeness auto
  1170 termination by (relation "measure fmsize") auto
  1171 
  1172 lemma simpfm[simp]: "Ifm bs (simpfm p) = Ifm bs p"
  1173 proof(induct p rule: simpfm.induct)
  1174   case (6 a) let ?sa = "simpnum a" have sa: "Inum bs ?sa = Inum bs a" by simp
  1175   {fix v assume "?sa = C v" hence ?case using sa by simp }
  1176   moreover {assume H:"\<not> (\<exists> v. ?sa = C v)"
  1177     let ?g = "numgcd ?sa"
  1178     let ?rsa = "reducecoeff ?sa"
  1179     let ?r = "Inum bs ?rsa"
  1180     have sa_nz: "nozerocoeff ?sa" by (rule simpnum_nz)
  1181     {assume gz: "?g=0" from numgcd_nz[OF sa_nz gz] H have "False" by auto}
  1182     with numgcd_pos[where t="?sa"] have "?g > 0" by (cases "?g=0", auto)
  1183     hence gp: "real ?g > 0" by simp
  1184     have "Inum bs ?sa = real ?g* ?r" by (simp add: reducecoeff)
  1185     with sa have "Inum bs a < 0 = (real ?g * ?r < real ?g * 0)" by simp
  1186     also have "\<dots> = (?r < 0)" using gp
  1187       by (simp only: mult_less_cancel_left) simp
  1188     finally have ?case using H by (cases "?sa" , simp_all add: Let_def)}
  1189   ultimately show ?case by blast
  1190 next
  1191   case (7 a)  let ?sa = "simpnum a" have sa: "Inum bs ?sa = Inum bs a" by simp
  1192   {fix v assume "?sa = C v" hence ?case using sa by simp }
  1193   moreover {assume H:"\<not> (\<exists> v. ?sa = C v)"
  1194     let ?g = "numgcd ?sa"
  1195     let ?rsa = "reducecoeff ?sa"
  1196     let ?r = "Inum bs ?rsa"
  1197     have sa_nz: "nozerocoeff ?sa" by (rule simpnum_nz)
  1198     {assume gz: "?g=0" from numgcd_nz[OF sa_nz gz] H have "False" by auto}
  1199     with numgcd_pos[where t="?sa"] have "?g > 0" by (cases "?g=0", auto)
  1200     hence gp: "real ?g > 0" by simp
  1201     have "Inum bs ?sa = real ?g* ?r" by (simp add: reducecoeff)
  1202     with sa have "Inum bs a \<le> 0 = (real ?g * ?r \<le> real ?g * 0)" by simp
  1203     also have "\<dots> = (?r \<le> 0)" using gp
  1204       by (simp only: mult_le_cancel_left) simp
  1205     finally have ?case using H by (cases "?sa" , simp_all add: Let_def)}
  1206   ultimately show ?case by blast
  1207 next
  1208   case (8 a)  let ?sa = "simpnum a" have sa: "Inum bs ?sa = Inum bs a" by simp
  1209   {fix v assume "?sa = C v" hence ?case using sa by simp }
  1210   moreover {assume H:"\<not> (\<exists> v. ?sa = C v)"
  1211     let ?g = "numgcd ?sa"
  1212     let ?rsa = "reducecoeff ?sa"
  1213     let ?r = "Inum bs ?rsa"
  1214     have sa_nz: "nozerocoeff ?sa" by (rule simpnum_nz)
  1215     {assume gz: "?g=0" from numgcd_nz[OF sa_nz gz] H have "False" by auto}
  1216     with numgcd_pos[where t="?sa"] have "?g > 0" by (cases "?g=0", auto)
  1217     hence gp: "real ?g > 0" by simp
  1218     have "Inum bs ?sa = real ?g* ?r" by (simp add: reducecoeff)
  1219     with sa have "Inum bs a > 0 = (real ?g * ?r > real ?g * 0)" by simp
  1220     also have "\<dots> = (?r > 0)" using gp
  1221       by (simp only: mult_less_cancel_left) simp
  1222     finally have ?case using H by (cases "?sa" , simp_all add: Let_def)}
  1223   ultimately show ?case by blast
  1224 next
  1225   case (9 a)  let ?sa = "simpnum a" have sa: "Inum bs ?sa = Inum bs a" by simp
  1226   {fix v assume "?sa = C v" hence ?case using sa by simp }
  1227   moreover {assume H:"\<not> (\<exists> v. ?sa = C v)"
  1228     let ?g = "numgcd ?sa"
  1229     let ?rsa = "reducecoeff ?sa"
  1230     let ?r = "Inum bs ?rsa"
  1231     have sa_nz: "nozerocoeff ?sa" by (rule simpnum_nz)
  1232     {assume gz: "?g=0" from numgcd_nz[OF sa_nz gz] H have "False" by auto}
  1233     with numgcd_pos[where t="?sa"] have "?g > 0" by (cases "?g=0", auto)
  1234     hence gp: "real ?g > 0" by simp
  1235     have "Inum bs ?sa = real ?g* ?r" by (simp add: reducecoeff)
  1236     with sa have "Inum bs a \<ge> 0 = (real ?g * ?r \<ge> real ?g * 0)" by simp
  1237     also have "\<dots> = (?r \<ge> 0)" using gp
  1238       by (simp only: mult_le_cancel_left) simp
  1239     finally have ?case using H by (cases "?sa" , simp_all add: Let_def)}
  1240   ultimately show ?case by blast
  1241 next
  1242   case (10 a)  let ?sa = "simpnum a" have sa: "Inum bs ?sa = Inum bs a" by simp
  1243   {fix v assume "?sa = C v" hence ?case using sa by simp }
  1244   moreover {assume H:"\<not> (\<exists> v. ?sa = C v)"
  1245     let ?g = "numgcd ?sa"
  1246     let ?rsa = "reducecoeff ?sa"
  1247     let ?r = "Inum bs ?rsa"
  1248     have sa_nz: "nozerocoeff ?sa" by (rule simpnum_nz)
  1249     {assume gz: "?g=0" from numgcd_nz[OF sa_nz gz] H have "False" by auto}
  1250     with numgcd_pos[where t="?sa"] have "?g > 0" by (cases "?g=0", auto)
  1251     hence gp: "real ?g > 0" by simp
  1252     have "Inum bs ?sa = real ?g* ?r" by (simp add: reducecoeff)
  1253     with sa have "Inum bs a = 0 = (real ?g * ?r = 0)" by simp
  1254     also have "\<dots> = (?r = 0)" using gp
  1255       by (simp add: mult_eq_0_iff)
  1256     finally have ?case using H by (cases "?sa" , simp_all add: Let_def)}
  1257   ultimately show ?case by blast
  1258 next
  1259   case (11 a)  let ?sa = "simpnum a" have sa: "Inum bs ?sa = Inum bs a" by simp
  1260   {fix v assume "?sa = C v" hence ?case using sa by simp }
  1261   moreover {assume H:"\<not> (\<exists> v. ?sa = C v)"
  1262     let ?g = "numgcd ?sa"
  1263     let ?rsa = "reducecoeff ?sa"
  1264     let ?r = "Inum bs ?rsa"
  1265     have sa_nz: "nozerocoeff ?sa" by (rule simpnum_nz)
  1266     {assume gz: "?g=0" from numgcd_nz[OF sa_nz gz] H have "False" by auto}
  1267     with numgcd_pos[where t="?sa"] have "?g > 0" by (cases "?g=0", auto)
  1268     hence gp: "real ?g > 0" by simp
  1269     have "Inum bs ?sa = real ?g* ?r" by (simp add: reducecoeff)
  1270     with sa have "Inum bs a \<noteq> 0 = (real ?g * ?r \<noteq> 0)" by simp
  1271     also have "\<dots> = (?r \<noteq> 0)" using gp
  1272       by (simp add: mult_eq_0_iff)
  1273     finally have ?case using H by (cases "?sa" , simp_all add: Let_def)}
  1274   ultimately show ?case by blast
  1275 next
  1276   case (12 i a)  let ?sa = "simpnum a"   have sa: "Inum bs ?sa = Inum bs a" by simp
  1277   have "i=0 \<or> (abs i = 1 \<and> check_int a) \<or> (i\<noteq>0 \<and> ((abs i \<noteq> 1) \<or> (\<not> check_int a)))" by auto
  1278   {assume "i=0" hence ?case using "12.hyps" by (simp add: rdvd_left_0_eq Let_def)}
  1279   moreover 
  1280   {assume ai1: "abs i = 1" and ai: "check_int a" 
  1281     hence "i=1 \<or> i= - 1" by arith
  1282     moreover {assume i1: "i = 1" 
  1283       from rdvd_left1_int[OF check_int[OF ai, simplified isint_iff]] 
  1284       have ?case using i1 ai by simp }
  1285     moreover {assume i1: "i = - 1" 
  1286       from rdvd_left1_int[OF check_int[OF ai, simplified isint_iff]] 
  1287         rdvd_abs1[where d="- 1" and t="Inum bs a"]
  1288       have ?case using i1 ai by simp }
  1289     ultimately have ?case by blast}
  1290   moreover   
  1291   {assume inz: "i\<noteq>0" and cond: "(abs i \<noteq> 1) \<or> (\<not> check_int a)"
  1292     {fix v assume "?sa = C v" hence ?case using sa[symmetric] inz cond
  1293         by (cases "abs i = 1", auto simp add: int_rdvd_iff) }
  1294     moreover {assume H:"\<not> (\<exists> v. ?sa = C v)" 
  1295       hence th: "simpfm (Dvd i a) = Dvd (fst (simpdvd i ?sa)) (snd (simpdvd i ?sa))" using inz cond by (cases ?sa, auto simp add: Let_def split_def)
  1296       from simpnum_nz have nz:"nozerocoeff ?sa" by simp
  1297       from simpdvd [OF nz inz] th have ?case using sa by simp}
  1298     ultimately have ?case by blast}
  1299   ultimately show ?case by blast
  1300 next
  1301   case (13 i a)  let ?sa = "simpnum a"   have sa: "Inum bs ?sa = Inum bs a" by simp
  1302   have "i=0 \<or> (abs i = 1 \<and> check_int a) \<or> (i\<noteq>0 \<and> ((abs i \<noteq> 1) \<or> (\<not> check_int a)))" by auto
  1303   {assume "i=0" hence ?case using "13.hyps" by (simp add: rdvd_left_0_eq Let_def)}
  1304   moreover 
  1305   {assume ai1: "abs i = 1" and ai: "check_int a" 
  1306     hence "i=1 \<or> i= - 1" by arith
  1307     moreover {assume i1: "i = 1" 
  1308       from rdvd_left1_int[OF check_int[OF ai, simplified isint_iff]] 
  1309       have ?case using i1 ai by simp }
  1310     moreover {assume i1: "i = - 1" 
  1311       from rdvd_left1_int[OF check_int[OF ai, simplified isint_iff]] 
  1312         rdvd_abs1[where d="- 1" and t="Inum bs a"]
  1313       have ?case using i1 ai by simp }
  1314     ultimately have ?case by blast}
  1315   moreover   
  1316   {assume inz: "i\<noteq>0" and cond: "(abs i \<noteq> 1) \<or> (\<not> check_int a)"
  1317     {fix v assume "?sa = C v" hence ?case using sa[symmetric] inz cond
  1318         by (cases "abs i = 1", auto simp add: int_rdvd_iff) }
  1319     moreover {assume H:"\<not> (\<exists> v. ?sa = C v)" 
  1320       hence th: "simpfm (NDvd i a) = NDvd (fst (simpdvd i ?sa)) (snd (simpdvd i ?sa))" using inz cond 
  1321         by (cases ?sa, auto simp add: Let_def split_def)
  1322       from simpnum_nz have nz:"nozerocoeff ?sa" by simp
  1323       from simpdvd [OF nz inz] th have ?case using sa by simp}
  1324     ultimately have ?case by blast}
  1325   ultimately show ?case by blast
  1326 qed (induct p rule: simpfm.induct, simp_all)
  1327 
  1328 lemma simpdvd_numbound0: "numbound0 t \<Longrightarrow> numbound0 (snd (simpdvd d t))"
  1329   by (simp add: simpdvd_def Let_def split_def reducecoeffh_numbound0)
  1330 
  1331 lemma simpfm_bound0[simp]: "bound0 p \<Longrightarrow> bound0 (simpfm p)"
  1332 proof(induct p rule: simpfm.induct)
  1333   case (6 a) hence nb: "numbound0 a" by simp
  1334   hence "numbound0 (simpnum a)" by (simp only: simpnum_numbound0[OF nb])
  1335   thus ?case by (cases "simpnum a", auto simp add: Let_def reducecoeff_numbound0)
  1336 next
  1337   case (7 a) hence nb: "numbound0 a" by simp
  1338   hence "numbound0 (simpnum a)" by (simp only: simpnum_numbound0[OF nb])
  1339   thus ?case by (cases "simpnum a", auto simp add: Let_def reducecoeff_numbound0)
  1340 next
  1341   case (8 a) hence nb: "numbound0 a" by simp
  1342   hence "numbound0 (simpnum a)" by (simp only: simpnum_numbound0[OF nb])
  1343   thus ?case by (cases "simpnum a", auto simp add: Let_def reducecoeff_numbound0)
  1344 next
  1345   case (9 a) hence nb: "numbound0 a" by simp
  1346   hence "numbound0 (simpnum a)" by (simp only: simpnum_numbound0[OF nb])
  1347   thus ?case by (cases "simpnum a", auto simp add: Let_def reducecoeff_numbound0)
  1348 next
  1349   case (10 a) hence nb: "numbound0 a" by simp
  1350   hence "numbound0 (simpnum a)" by (simp only: simpnum_numbound0[OF nb])
  1351   thus ?case by (cases "simpnum a", auto simp add: Let_def reducecoeff_numbound0)
  1352 next
  1353   case (11 a) hence nb: "numbound0 a" by simp
  1354   hence "numbound0 (simpnum a)" by (simp only: simpnum_numbound0[OF nb])
  1355   thus ?case by (cases "simpnum a", auto simp add: Let_def reducecoeff_numbound0)
  1356 next
  1357   case (12 i a) hence nb: "numbound0 a" by simp
  1358   hence "numbound0 (simpnum a)" by (simp only: simpnum_numbound0[OF nb])
  1359   thus ?case by (cases "simpnum a", auto simp add: Let_def reducecoeff_numbound0 simpdvd_numbound0 split_def)
  1360 next
  1361   case (13 i a) hence nb: "numbound0 a" by simp
  1362   hence "numbound0 (simpnum a)" by (simp only: simpnum_numbound0[OF nb])
  1363   thus ?case by (cases "simpnum a", auto simp add: Let_def reducecoeff_numbound0 simpdvd_numbound0 split_def)
  1364 qed(auto simp add: disj_def imp_def iff_def conj_def)
  1365 
  1366 lemma simpfm_qf[simp]: "qfree p \<Longrightarrow> qfree (simpfm p)"
  1367 by (induct p rule: simpfm.induct, auto simp add: Let_def)
  1368 (case_tac "simpnum a",auto simp add: split_def Let_def)+
  1369 
  1370 
  1371   (* Generic quantifier elimination *)
  1372 
  1373 definition list_conj :: "fm list \<Rightarrow> fm" where
  1374   "list_conj ps \<equiv> foldr conj ps T"
  1375 lemma list_conj: "Ifm bs (list_conj ps) = (\<forall>p\<in> set ps. Ifm bs p)"
  1376   by (induct ps, auto simp add: list_conj_def)
  1377 lemma list_conj_qf: " \<forall>p\<in> set ps. qfree p \<Longrightarrow> qfree (list_conj ps)"
  1378   by (induct ps, auto simp add: list_conj_def)
  1379 lemma list_conj_nb: " \<forall>p\<in> set ps. bound0 p \<Longrightarrow> bound0 (list_conj ps)"
  1380   by (induct ps, auto simp add: list_conj_def)
  1381 definition CJNB :: "(fm \<Rightarrow> fm) \<Rightarrow> fm \<Rightarrow> fm" where
  1382   "CJNB f p \<equiv> (let cjs = conjuncts p ; (yes,no) = List.partition bound0 cjs
  1383                    in conj (decr (list_conj yes)) (f (list_conj no)))"
  1384 
  1385 lemma CJNB_qe: 
  1386   assumes qe: "\<forall> bs p. qfree p \<longrightarrow> qfree (qe p) \<and> (Ifm bs (qe p) = Ifm bs (E p))"
  1387   shows "\<forall> bs p. qfree p \<longrightarrow> qfree (CJNB qe p) \<and> (Ifm bs ((CJNB qe p)) = Ifm bs (E p))"
  1388 proof(clarify)
  1389   fix bs p
  1390   assume qfp: "qfree p"
  1391   let ?cjs = "conjuncts p"
  1392   let ?yes = "fst (List.partition bound0 ?cjs)"
  1393   let ?no = "snd (List.partition bound0 ?cjs)"
  1394   let ?cno = "list_conj ?no"
  1395   let ?cyes = "list_conj ?yes"
  1396   have part: "List.partition bound0 ?cjs = (?yes,?no)" by simp
  1397   from partition_P[OF part] have "\<forall> q\<in> set ?yes. bound0 q" by blast 
  1398   hence yes_nb: "bound0 ?cyes" by (simp add: list_conj_nb) 
  1399   hence yes_qf: "qfree (decr ?cyes )" by (simp add: decr_qf)
  1400   from conjuncts_qf[OF qfp] partition_set[OF part] 
  1401   have " \<forall>q\<in> set ?no. qfree q" by auto
  1402   hence no_qf: "qfree ?cno"by (simp add: list_conj_qf)
  1403   with qe have cno_qf:"qfree (qe ?cno )" 
  1404     and noE: "Ifm bs (qe ?cno) = Ifm bs (E ?cno)" by blast+
  1405   from cno_qf yes_qf have qf: "qfree (CJNB qe p)" 
  1406     by (simp add: CJNB_def Let_def conj_qf split_def)
  1407   {fix bs
  1408     from conjuncts have "Ifm bs p = (\<forall>q\<in> set ?cjs. Ifm bs q)" by blast
  1409     also have "\<dots> = ((\<forall>q\<in> set ?yes. Ifm bs q) \<and> (\<forall>q\<in> set ?no. Ifm bs q))"
  1410       using partition_set[OF part] by auto
  1411     finally have "Ifm bs p = ((Ifm bs ?cyes) \<and> (Ifm bs ?cno))" using list_conj by simp}
  1412   hence "Ifm bs (E p) = (\<exists>x. (Ifm (x#bs) ?cyes) \<and> (Ifm (x#bs) ?cno))" by simp
  1413   also fix y have "\<dots> = (\<exists>x. (Ifm (y#bs) ?cyes) \<and> (Ifm (x#bs) ?cno))"
  1414     using bound0_I[OF yes_nb, where bs="bs" and b'="y"] by blast
  1415   also have "\<dots> = (Ifm bs (decr ?cyes) \<and> Ifm bs (E ?cno))"
  1416     by (auto simp add: decr[OF yes_nb] simp del: partition_filter_conv)
  1417   also have "\<dots> = (Ifm bs (conj (decr ?cyes) (qe ?cno)))"
  1418     using qe[rule_format, OF no_qf] by auto
  1419   finally have "Ifm bs (E p) = Ifm bs (CJNB qe p)" 
  1420     by (simp add: Let_def CJNB_def split_def)
  1421   with qf show "qfree (CJNB qe p) \<and> Ifm bs (CJNB qe p) = Ifm bs (E p)" by blast
  1422 qed
  1423 
  1424 function (sequential) qelim :: "fm \<Rightarrow> (fm \<Rightarrow> fm) \<Rightarrow> fm" where
  1425   "qelim (E p) = (\<lambda> qe. DJ (CJNB qe) (qelim p qe))"
  1426 | "qelim (A p) = (\<lambda> qe. not (qe ((qelim (NOT p) qe))))"
  1427 | "qelim (NOT p) = (\<lambda> qe. not (qelim p qe))"
  1428 | "qelim (And p q) = (\<lambda> qe. conj (qelim p qe) (qelim q qe))" 
  1429 | "qelim (Or  p q) = (\<lambda> qe. disj (qelim p qe) (qelim q qe))" 
  1430 | "qelim (Imp p q) = (\<lambda> qe. disj (qelim (NOT p) qe) (qelim q qe))"
  1431 | "qelim (Iff p q) = (\<lambda> qe. iff (qelim p qe) (qelim q qe))"
  1432 | "qelim p = (\<lambda> y. simpfm p)"
  1433 by pat_completeness auto
  1434 termination by (relation "measure fmsize") auto
  1435 
  1436 lemma qelim_ci:
  1437   assumes qe_inv: "\<forall> bs p. qfree p \<longrightarrow> qfree (qe p) \<and> (Ifm bs (qe p) = Ifm bs (E p))"
  1438   shows "\<And> bs. qfree (qelim p qe) \<and> (Ifm bs (qelim p qe) = Ifm bs p)"
  1439   using qe_inv DJ_qe[OF CJNB_qe[OF qe_inv]] 
  1440   by (induct p rule: qelim.induct) (auto simp del: simpfm.simps)
  1441 
  1442 
  1443 text {* The @{text "\<int>"} Part *}
  1444 text{* Linearity for fm where Bound 0 ranges over @{text "\<int>"} *}
  1445 
  1446 function zsplit0 :: "num \<Rightarrow> int \<times> num" (* splits the bounded from the unbounded part*) where
  1447   "zsplit0 (C c) = (0,C c)"
  1448 | "zsplit0 (Bound n) = (if n=0 then (1, C 0) else (0,Bound n))"
  1449 | "zsplit0 (CN n c a) = zsplit0 (Add (Mul c (Bound n)) a)"
  1450 | "zsplit0 (CF c a b) = zsplit0 (Add (Mul c (Floor a)) b)"
  1451 | "zsplit0 (Neg a) = (let (i',a') =  zsplit0 a in (-i', Neg a'))"
  1452 | "zsplit0 (Add a b) = (let (ia,a') =  zsplit0 a ; 
  1453                             (ib,b') =  zsplit0 b 
  1454                             in (ia+ib, Add a' b'))"
  1455 | "zsplit0 (Sub a b) = (let (ia,a') =  zsplit0 a ; 
  1456                             (ib,b') =  zsplit0 b 
  1457                             in (ia-ib, Sub a' b'))"
  1458 | "zsplit0 (Mul i a) = (let (i',a') =  zsplit0 a in (i*i', Mul i a'))"
  1459 | "zsplit0 (Floor a) = (let (i',a') =  zsplit0 a in (i',Floor a'))"
  1460 by pat_completeness auto
  1461 termination by (relation "measure num_size") auto
  1462 
  1463 lemma zsplit0_I:
  1464   shows "\<And> n a. zsplit0 t = (n,a) \<Longrightarrow> (Inum ((real (x::int)) #bs) (CN 0 n a) = Inum (real x #bs) t) \<and> numbound0 a"
  1465   (is "\<And> n a. ?S t = (n,a) \<Longrightarrow> (?I x (CN 0 n a) = ?I x t) \<and> ?N a")
  1466 proof(induct t rule: zsplit0.induct)
  1467   case (1 c n a) thus ?case by auto 
  1468 next
  1469   case (2 m n a) thus ?case by (cases "m=0") auto
  1470 next
  1471   case (3 n i a n a') thus ?case by auto
  1472 next 
  1473   case (4 c a b n a') thus ?case by auto
  1474 next
  1475   case (5 t n a)
  1476   let ?nt = "fst (zsplit0 t)"
  1477   let ?at = "snd (zsplit0 t)"
  1478   have abj: "zsplit0 t = (?nt,?at)" by simp hence th: "a=Neg ?at \<and> n=-?nt" using 5 
  1479     by (simp add: Let_def split_def)
  1480   from abj 5 have th2: "(?I x (CN 0 ?nt ?at) = ?I x t) \<and> ?N ?at" by blast
  1481   from th2[simplified] th[simplified] show ?case by simp
  1482 next
  1483   case (6 s t n a)
  1484   let ?ns = "fst (zsplit0 s)"
  1485   let ?as = "snd (zsplit0 s)"
  1486   let ?nt = "fst (zsplit0 t)"
  1487   let ?at = "snd (zsplit0 t)"
  1488   have abjs: "zsplit0 s = (?ns,?as)" by simp 
  1489   moreover have abjt:  "zsplit0 t = (?nt,?at)" by simp 
  1490   ultimately have th: "a=Add ?as ?at \<and> n=?ns + ?nt" using 6
  1491     by (simp add: Let_def split_def)
  1492   from abjs[symmetric] have bluddy: "\<exists> x y. (x,y) = zsplit0 s" by blast
  1493   from 6 have "(\<exists> x y. (x,y) = zsplit0 s) \<longrightarrow> (\<forall>xa xb. zsplit0 t = (xa, xb) \<longrightarrow> Inum (real x # bs) (CN 0 xa xb) = Inum (real x # bs) t \<and> numbound0 xb)" by blast (*FIXME*)
  1494   with bluddy abjt have th3: "(?I x (CN 0 ?nt ?at) = ?I x t) \<and> ?N ?at" by blast
  1495   from abjs 6  have th2: "(?I x (CN 0 ?ns ?as) = ?I x s) \<and> ?N ?as" by blast
  1496   from th3[simplified] th2[simplified] th[simplified] show ?case 
  1497     by (simp add: left_distrib)
  1498 next
  1499   case (7 s t n a)
  1500   let ?ns = "fst (zsplit0 s)"
  1501   let ?as = "snd (zsplit0 s)"
  1502   let ?nt = "fst (zsplit0 t)"
  1503   let ?at = "snd (zsplit0 t)"
  1504   have abjs: "zsplit0 s = (?ns,?as)" by simp 
  1505   moreover have abjt:  "zsplit0 t = (?nt,?at)" by simp 
  1506   ultimately have th: "a=Sub ?as ?at \<and> n=?ns - ?nt" using 7
  1507     by (simp add: Let_def split_def)
  1508   from abjs[symmetric] have bluddy: "\<exists> x y. (x,y) = zsplit0 s" by blast
  1509   from 7 have "(\<exists> x y. (x,y) = zsplit0 s) \<longrightarrow> (\<forall>xa xb. zsplit0 t = (xa, xb) \<longrightarrow> Inum (real x # bs) (CN 0 xa xb) = Inum (real x # bs) t \<and> numbound0 xb)" by blast (*FIXME*)
  1510   with bluddy abjt have th3: "(?I x (CN 0 ?nt ?at) = ?I x t) \<and> ?N ?at" by blast
  1511   from abjs 7 have th2: "(?I x (CN 0 ?ns ?as) = ?I x s) \<and> ?N ?as" by blast
  1512   from th3[simplified] th2[simplified] th[simplified] show ?case 
  1513     by (simp add: left_diff_distrib)
  1514 next
  1515   case (8 i t n a)
  1516   let ?nt = "fst (zsplit0 t)"
  1517   let ?at = "snd (zsplit0 t)"
  1518   have abj: "zsplit0 t = (?nt,?at)" by simp hence th: "a=Mul i ?at \<and> n=i*?nt" using 8
  1519     by (simp add: Let_def split_def)
  1520   from abj 8 have th2: "(?I x (CN 0 ?nt ?at) = ?I x t) \<and> ?N ?at" by blast
  1521   hence "?I x (Mul i t) = (real i) * ?I x (CN 0 ?nt ?at)" by simp
  1522   also have "\<dots> = ?I x (CN 0 (i*?nt) (Mul i ?at))" by (simp add: right_distrib)
  1523   finally show ?case using th th2 by simp
  1524 next
  1525   case (9 t n a)
  1526   let ?nt = "fst (zsplit0 t)"
  1527   let ?at = "snd (zsplit0 t)"
  1528   have abj: "zsplit0 t = (?nt,?at)" by simp hence th: "a= Floor ?at \<and> n=?nt" using 9
  1529     by (simp add: Let_def split_def)
  1530   from abj 9 have th2: "(?I x (CN 0 ?nt ?at) = ?I x t) \<and> ?N ?at" by blast
  1531   hence na: "?N a" using th by simp
  1532   have th': "(real ?nt)*(real x) = real (?nt * x)" by simp
  1533   have "?I x (Floor t) = ?I x (Floor (CN 0 ?nt ?at))" using th2 by simp
  1534   also have "\<dots> = real (floor ((real ?nt)* real(x) + ?I x ?at))" by simp
  1535   also have "\<dots> = real (floor (?I x ?at + real (?nt* x)))" by (simp add: add_ac)
  1536   also have "\<dots> = real (floor (?I x ?at) + (?nt* x))" 
  1537     using floor_add[where x="?I x ?at" and a="?nt* x"] by simp 
  1538   also have "\<dots> = real (?nt)*(real x) + real (floor (?I x ?at))" by (simp add: add_ac)
  1539   finally have "?I x (Floor t) = ?I x (CN 0 n a)" using th by simp
  1540   with na show ?case by simp
  1541 qed
  1542 
  1543 consts
  1544   iszlfm :: "fm \<Rightarrow> real list \<Rightarrow> bool"   (* Linearity test for fm *)
  1545   zlfm :: "fm \<Rightarrow> fm"       (* Linearity transformation for fm *)
  1546 recdef iszlfm "measure size"
  1547   "iszlfm (And p q) = (\<lambda> bs. iszlfm p bs \<and> iszlfm q bs)" 
  1548   "iszlfm (Or p q) = (\<lambda> bs. iszlfm p bs \<and> iszlfm q bs)" 
  1549   "iszlfm (Eq  (CN 0 c e)) = (\<lambda> bs. c>0 \<and> numbound0 e \<and> isint e bs)"
  1550   "iszlfm (NEq (CN 0 c e)) = (\<lambda> bs. c>0 \<and> numbound0 e \<and> isint e bs)"
  1551   "iszlfm (Lt  (CN 0 c e)) = (\<lambda> bs. c>0 \<and> numbound0 e \<and> isint e bs)"
  1552   "iszlfm (Le  (CN 0 c e)) = (\<lambda> bs. c>0 \<and> numbound0 e \<and> isint e bs)"
  1553   "iszlfm (Gt  (CN 0 c e)) = (\<lambda> bs. c>0 \<and> numbound0 e \<and> isint e bs)"
  1554   "iszlfm (Ge  (CN 0 c e)) = (\<lambda> bs. c>0 \<and> numbound0 e \<and> isint e bs)"
  1555   "iszlfm (Dvd i (CN 0 c e)) = 
  1556                  (\<lambda> bs. c>0 \<and> i>0 \<and> numbound0 e \<and> isint e bs)"
  1557   "iszlfm (NDvd i (CN 0 c e))= 
  1558                  (\<lambda> bs. c>0 \<and> i>0 \<and> numbound0 e \<and> isint e bs)"
  1559   "iszlfm p = (\<lambda> bs. isatom p \<and> (bound0 p))"
  1560 
  1561 lemma zlin_qfree: "iszlfm p bs \<Longrightarrow> qfree p"
  1562   by (induct p rule: iszlfm.induct) auto
  1563 
  1564 lemma iszlfm_gen:
  1565   assumes lp: "iszlfm p (x#bs)"
  1566   shows "\<forall> y. iszlfm p (y#bs)"
  1567 proof
  1568   fix y
  1569   show "iszlfm p (y#bs)"
  1570     using lp
  1571   by(induct p rule: iszlfm.induct, simp_all add: numbound0_gen[rule_format, where x="x" and y="y"])
  1572 qed
  1573 
  1574 lemma conj_zl[simp]: "iszlfm p bs \<Longrightarrow> iszlfm q bs \<Longrightarrow> iszlfm (conj p q) bs"
  1575   using conj_def by (cases p,auto)
  1576 lemma disj_zl[simp]: "iszlfm p bs \<Longrightarrow> iszlfm q bs \<Longrightarrow> iszlfm (disj p q) bs"
  1577   using disj_def by (cases p,auto)
  1578 
  1579 recdef zlfm "measure fmsize"
  1580   "zlfm (And p q) = conj (zlfm p) (zlfm q)"
  1581   "zlfm (Or p q) = disj (zlfm p) (zlfm q)"
  1582   "zlfm (Imp p q) = disj (zlfm (NOT p)) (zlfm q)"
  1583   "zlfm (Iff p q) = disj (conj (zlfm p) (zlfm q)) (conj (zlfm (NOT p)) (zlfm (NOT q)))"
  1584   "zlfm (Lt a) = (let (c,r) = zsplit0 a in 
  1585      if c=0 then Lt r else 
  1586      if c>0 then Or (Lt (CN 0 c (Neg (Floor (Neg r))))) (And (Eq (CN 0 c (Neg (Floor (Neg r))))) (Lt (Add (Floor (Neg r)) r))) 
  1587      else Or (Gt (CN 0 (-c) (Floor(Neg r)))) (And (Eq(CN 0 (-c) (Floor(Neg r)))) (Lt (Add (Floor (Neg r)) r))))"
  1588   "zlfm (Le a) = (let (c,r) = zsplit0 a in 
  1589      if c=0 then Le r else 
  1590      if c>0 then Or (Le (CN 0 c (Neg (Floor (Neg r))))) (And (Eq (CN 0 c (Neg (Floor (Neg r))))) (Lt (Add (Floor (Neg r)) r))) 
  1591      else Or (Ge (CN 0 (-c) (Floor(Neg r)))) (And (Eq(CN 0 (-c) (Floor(Neg r)))) (Lt (Add (Floor (Neg r)) r))))"
  1592   "zlfm (Gt a) = (let (c,r) = zsplit0 a in 
  1593      if c=0 then Gt r else 
  1594      if c>0 then Or (Gt (CN 0 c (Floor r))) (And (Eq (CN 0 c (Floor r))) (Lt (Sub (Floor r) r))) 
  1595      else Or (Lt (CN 0 (-c) (Neg (Floor r)))) (And (Eq(CN 0 (-c) (Neg (Floor r)))) (Lt (Sub (Floor r) r))))"
  1596   "zlfm (Ge a) = (let (c,r) = zsplit0 a in 
  1597      if c=0 then Ge r else 
  1598      if c>0 then Or (Ge (CN 0 c (Floor r))) (And (Eq (CN 0 c (Floor r))) (Lt (Sub (Floor r) r))) 
  1599      else Or (Le (CN 0 (-c) (Neg (Floor r)))) (And (Eq(CN 0 (-c) (Neg (Floor r)))) (Lt (Sub (Floor r) r))))"
  1600   "zlfm (Eq a) = (let (c,r) = zsplit0 a in 
  1601               if c=0 then Eq r else 
  1602       if c>0 then (And (Eq (CN 0 c (Neg (Floor (Neg r))))) (Eq (Add (Floor (Neg r)) r)))
  1603       else (And (Eq (CN 0 (-c) (Floor (Neg r)))) (Eq (Add (Floor (Neg r)) r))))"
  1604   "zlfm (NEq a) = (let (c,r) = zsplit0 a in 
  1605               if c=0 then NEq r else 
  1606       if c>0 then (Or (NEq (CN 0 c (Neg (Floor (Neg r))))) (NEq (Add (Floor (Neg r)) r)))
  1607       else (Or (NEq (CN 0 (-c) (Floor (Neg r)))) (NEq (Add (Floor (Neg r)) r))))"
  1608   "zlfm (Dvd i a) = (if i=0 then zlfm (Eq a) 
  1609   else (let (c,r) = zsplit0 a in 
  1610               if c=0 then Dvd (abs i) r else 
  1611       if c>0 then And (Eq (Sub (Floor r) r)) (Dvd (abs i) (CN 0 c (Floor r))) 
  1612       else And (Eq (Sub (Floor r) r)) (Dvd (abs i) (CN 0 (-c) (Neg (Floor r))))))"
  1613   "zlfm (NDvd i a) = (if i=0 then zlfm (NEq a) 
  1614   else (let (c,r) = zsplit0 a in 
  1615               if c=0 then NDvd (abs i) r else 
  1616       if c>0 then Or (NEq (Sub (Floor r) r)) (NDvd (abs i) (CN 0 c (Floor r))) 
  1617       else Or (NEq (Sub (Floor r) r)) (NDvd (abs i) (CN 0 (-c) (Neg (Floor r))))))"
  1618   "zlfm (NOT (And p q)) = disj (zlfm (NOT p)) (zlfm (NOT q))"
  1619   "zlfm (NOT (Or p q)) = conj (zlfm (NOT p)) (zlfm (NOT q))"
  1620   "zlfm (NOT (Imp p q)) = conj (zlfm p) (zlfm (NOT q))"
  1621   "zlfm (NOT (Iff p q)) = disj (conj(zlfm p) (zlfm(NOT q))) (conj (zlfm(NOT p)) (zlfm q))"
  1622   "zlfm (NOT (NOT p)) = zlfm p"
  1623   "zlfm (NOT T) = F"
  1624   "zlfm (NOT F) = T"
  1625   "zlfm (NOT (Lt a)) = zlfm (Ge a)"
  1626   "zlfm (NOT (Le a)) = zlfm (Gt a)"
  1627   "zlfm (NOT (Gt a)) = zlfm (Le a)"
  1628   "zlfm (NOT (Ge a)) = zlfm (Lt a)"
  1629   "zlfm (NOT (Eq a)) = zlfm (NEq a)"
  1630   "zlfm (NOT (NEq a)) = zlfm (Eq a)"
  1631   "zlfm (NOT (Dvd i a)) = zlfm (NDvd i a)"
  1632   "zlfm (NOT (NDvd i a)) = zlfm (Dvd i a)"
  1633   "zlfm p = p" (hints simp add: fmsize_pos)
  1634 
  1635 lemma split_int_less_real: 
  1636   "(real (a::int) < b) = (a < floor b \<or> (a = floor b \<and> real (floor b) < b))"
  1637 proof( auto)
  1638   assume alb: "real a < b" and agb: "\<not> a < floor b"
  1639   from agb have "floor b \<le> a" by simp hence th: "b < real a + 1" by (simp only: floor_le_eq)
  1640   from floor_eq[OF alb th] show "a= floor b" by simp 
  1641 next
  1642   assume alb: "a < floor b"
  1643   hence "real a < real (floor b)" by simp
  1644   moreover have "real (floor b) \<le> b" by simp ultimately show  "real a < b" by arith 
  1645 qed
  1646 
  1647 lemma split_int_less_real': 
  1648   "(real (a::int) + b < 0) = (real a - real (floor(-b)) < 0 \<or> (real a - real (floor (-b)) = 0 \<and> real (floor (-b)) + b < 0))"
  1649 proof- 
  1650   have "(real a + b <0) = (real a < -b)" by arith
  1651   with split_int_less_real[where a="a" and b="-b"] show ?thesis by arith  
  1652 qed
  1653 
  1654 lemma split_int_gt_real': 
  1655   "(real (a::int) + b > 0) = (real a + real (floor b) > 0 \<or> (real a + real (floor b) = 0 \<and> real (floor b) - b < 0))"
  1656 proof- 
  1657   have th: "(real a + b >0) = (real (-a) + (-b)< 0)" by arith
  1658   show ?thesis using myless[of _ "real (floor b)"] 
  1659     by (simp only:th split_int_less_real'[where a="-a" and b="-b"]) 
  1660     (simp add: algebra_simps diff_minus[symmetric],arith)
  1661 qed
  1662 
  1663 lemma split_int_le_real: 
  1664   "(real (a::int) \<le> b) = (a \<le> floor b \<or> (a = floor b \<and> real (floor b) < b))"
  1665 proof( auto)
  1666   assume alb: "real a \<le> b" and agb: "\<not> a \<le> floor b"
  1667   from alb have "floor (real a) \<le> floor b " by (simp only: floor_mono) 
  1668   hence "a \<le> floor b" by simp with agb show "False" by simp
  1669 next
  1670   assume alb: "a \<le> floor b"
  1671   hence "real a \<le> real (floor b)" by (simp only: floor_mono)
  1672   also have "\<dots>\<le> b" by simp  finally show  "real a \<le> b" . 
  1673 qed
  1674 
  1675 lemma split_int_le_real': 
  1676   "(real (a::int) + b \<le> 0) = (real a - real (floor(-b)) \<le> 0 \<or> (real a - real (floor (-b)) = 0 \<and> real (floor (-b)) + b < 0))"
  1677 proof- 
  1678   have "(real a + b \<le>0) = (real a \<le> -b)" by arith
  1679   with split_int_le_real[where a="a" and b="-b"] show ?thesis by arith  
  1680 qed
  1681 
  1682 lemma split_int_ge_real': 
  1683   "(real (a::int) + b \<ge> 0) = (real a + real (floor b) \<ge> 0 \<or> (real a + real (floor b) = 0 \<and> real (floor b) - b < 0))"
  1684 proof- 
  1685   have th: "(real a + b \<ge>0) = (real (-a) + (-b) \<le> 0)" by arith
  1686   show ?thesis by (simp only: th split_int_le_real'[where a="-a" and b="-b"])
  1687     (simp add: algebra_simps diff_minus[symmetric],arith)
  1688 qed
  1689 
  1690 lemma split_int_eq_real: "(real (a::int) = b) = ( a = floor b \<and> b = real (floor b))" (is "?l = ?r")
  1691 by auto
  1692 
  1693 lemma split_int_eq_real': "(real (a::int) + b = 0) = ( a - floor (-b) = 0 \<and> real (floor (-b)) + b = 0)" (is "?l = ?r")
  1694 proof-
  1695   have "?l = (real a = -b)" by arith
  1696   with split_int_eq_real[where a="a" and b="-b"] show ?thesis by simp arith
  1697 qed
  1698 
  1699 lemma zlfm_I:
  1700   assumes qfp: "qfree p"
  1701   shows "(Ifm (real i #bs) (zlfm p) = Ifm (real i# bs) p) \<and> iszlfm (zlfm p) (real (i::int) #bs)"
  1702   (is "(?I (?l p) = ?I p) \<and> ?L (?l p)")
  1703 using qfp
  1704 proof(induct p rule: zlfm.induct)
  1705   case (5 a) 
  1706   let ?c = "fst (zsplit0 a)"
  1707   let ?r = "snd (zsplit0 a)"
  1708   have spl: "zsplit0 a = (?c,?r)" by simp
  1709   from zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1710   have Ia:"Inum (real i # bs) a = Inum (real i #bs) (CN 0 ?c ?r)" and nb: "numbound0 ?r" by auto 
  1711   let ?N = "\<lambda> t. Inum (real i#bs) t"
  1712   have "?c = 0 \<or> (?c >0 \<and> ?c\<noteq>0) \<or> (?c<0 \<and> ?c\<noteq>0)" by arith
  1713   moreover
  1714   {assume "?c=0" hence ?case using zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1715       by (cases "?r", simp_all add: Let_def split_def,case_tac "nat", simp_all)}
  1716   moreover
  1717   {assume cp: "?c > 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (Lt a))" 
  1718       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1719     have "?I (Lt a) = (real (?c * i) + (?N ?r) < 0)" using Ia by (simp add: Let_def split_def)
  1720     also have "\<dots> = (?I (?l (Lt a)))" apply (simp only: split_int_less_real'[where a="?c*i" and b="?N ?r"]) by (simp add: Ia cp cnz Let_def split_def diff_minus)
  1721     finally have ?case using l by simp}
  1722   moreover
  1723   {assume cn: "?c < 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (Lt a))" 
  1724       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1725     have "?I (Lt a) = (real (?c * i) + (?N ?r) < 0)" using Ia by (simp add: Let_def split_def)
  1726     also from cn cnz have "\<dots> = (?I (?l (Lt a)))" by (simp only: split_int_less_real'[where a="?c*i" and b="?N ?r"]) (simp add: Ia Let_def split_def diff_minus[symmetric] add_ac, arith)
  1727     finally have ?case using l by simp}
  1728   ultimately show ?case by blast
  1729 next
  1730   case (6 a)
  1731   let ?c = "fst (zsplit0 a)"
  1732   let ?r = "snd (zsplit0 a)"
  1733   have spl: "zsplit0 a = (?c,?r)" by simp
  1734   from zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1735   have Ia:"Inum (real i # bs) a = Inum (real i #bs) (CN 0 ?c ?r)" and nb: "numbound0 ?r" by auto 
  1736   let ?N = "\<lambda> t. Inum (real i#bs) t"
  1737   have "?c = 0 \<or> (?c >0 \<and> ?c\<noteq>0) \<or> (?c<0 \<and> ?c\<noteq>0)" by arith
  1738   moreover
  1739   {assume "?c=0" hence ?case using zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1740       by (cases "?r", simp_all add: Let_def split_def, case_tac "nat",simp_all)}
  1741   moreover
  1742   {assume cp: "?c > 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (Le a))" 
  1743       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1744     have "?I (Le a) = (real (?c * i) + (?N ?r) \<le> 0)" using Ia by (simp add: Let_def split_def)
  1745     also have "\<dots> = (?I (?l (Le a)))" by (simp only: split_int_le_real'[where a="?c*i" and b="?N ?r"]) (simp add: Ia cp cnz Let_def split_def diff_minus)
  1746     finally have ?case using l by simp}
  1747   moreover
  1748   {assume cn: "?c < 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (Le a))" 
  1749       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1750     have "?I (Le a) = (real (?c * i) + (?N ?r) \<le> 0)" using Ia by (simp add: Let_def split_def)
  1751     also from cn cnz have "\<dots> = (?I (?l (Le a)))" by (simp only: split_int_le_real'[where a="?c*i" and b="?N ?r"]) (simp add: Ia Let_def split_def diff_minus[symmetric] add_ac ,arith)
  1752     finally have ?case using l by simp}
  1753   ultimately show ?case by blast
  1754 next
  1755   case (7 a) 
  1756   let ?c = "fst (zsplit0 a)"
  1757   let ?r = "snd (zsplit0 a)"
  1758   have spl: "zsplit0 a = (?c,?r)" by simp
  1759   from zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1760   have Ia:"Inum (real i # bs) a = Inum (real i #bs) (CN 0 ?c ?r)" and nb: "numbound0 ?r" by auto 
  1761   let ?N = "\<lambda> t. Inum (real i#bs) t"
  1762   have "?c = 0 \<or> (?c >0 \<and> ?c\<noteq>0) \<or> (?c<0 \<and> ?c\<noteq>0)" by arith
  1763   moreover
  1764   {assume "?c=0" hence ?case using zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1765       by (cases "?r", simp_all add: Let_def split_def, case_tac "nat", simp_all)}
  1766   moreover
  1767   {assume cp: "?c > 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (Gt a))" 
  1768       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1769     have "?I (Gt a) = (real (?c * i) + (?N ?r) > 0)" using Ia by (simp add: Let_def split_def)
  1770     also have "\<dots> = (?I (?l (Gt a)))" by (simp only: split_int_gt_real'[where a="?c*i" and b="?N ?r"]) (simp add: Ia cp cnz Let_def split_def diff_minus)
  1771     finally have ?case using l by simp}
  1772   moreover
  1773   {assume cn: "?c < 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (Gt a))" 
  1774       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1775     have "?I (Gt a) = (real (?c * i) + (?N ?r) > 0)" using Ia by (simp add: Let_def split_def)
  1776     also from cn cnz have "\<dots> = (?I (?l (Gt a)))" by (simp only: split_int_gt_real'[where a="?c*i" and b="?N ?r"]) (simp add: Ia Let_def split_def diff_minus[symmetric] add_ac, arith)
  1777     finally have ?case using l by simp}
  1778   ultimately show ?case by blast
  1779 next
  1780   case (8 a)
  1781    let ?c = "fst (zsplit0 a)"
  1782   let ?r = "snd (zsplit0 a)"
  1783   have spl: "zsplit0 a = (?c,?r)" by simp
  1784   from zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1785   have Ia:"Inum (real i # bs) a = Inum (real i #bs) (CN 0 ?c ?r)" and nb: "numbound0 ?r" by auto 
  1786   let ?N = "\<lambda> t. Inum (real i#bs) t"
  1787   have "?c = 0 \<or> (?c >0 \<and> ?c\<noteq>0) \<or> (?c<0 \<and> ?c\<noteq>0)" by arith
  1788   moreover
  1789   {assume "?c=0" hence ?case using zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1790       by (cases "?r", simp_all add: Let_def split_def, case_tac "nat", simp_all)}
  1791   moreover
  1792   {assume cp: "?c > 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (Ge a))" 
  1793       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1794     have "?I (Ge a) = (real (?c * i) + (?N ?r) \<ge> 0)" using Ia by (simp add: Let_def split_def)
  1795     also have "\<dots> = (?I (?l (Ge a)))" by (simp only: split_int_ge_real'[where a="?c*i" and b="?N ?r"]) (simp add: Ia cp cnz Let_def split_def diff_minus)
  1796     finally have ?case using l by simp}
  1797   moreover
  1798   {assume cn: "?c < 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (Ge a))" 
  1799       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1800     have "?I (Ge a) = (real (?c * i) + (?N ?r) \<ge> 0)" using Ia by (simp add: Let_def split_def)
  1801     also from cn cnz have "\<dots> = (?I (?l (Ge a)))" by (simp only: split_int_ge_real'[where a="?c*i" and b="?N ?r"]) (simp add: Ia Let_def split_def diff_minus[symmetric] add_ac, arith)
  1802     finally have ?case using l by simp}
  1803   ultimately show ?case by blast
  1804 next
  1805   case (9 a)
  1806   let ?c = "fst (zsplit0 a)"
  1807   let ?r = "snd (zsplit0 a)"
  1808   have spl: "zsplit0 a = (?c,?r)" by simp
  1809   from zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1810   have Ia:"Inum (real i # bs) a = Inum (real i #bs) (CN 0 ?c ?r)" and nb: "numbound0 ?r" by auto 
  1811   let ?N = "\<lambda> t. Inum (real i#bs) t"
  1812   have "?c = 0 \<or> (?c >0 \<and> ?c\<noteq>0) \<or> (?c<0 \<and> ?c\<noteq>0)" by arith
  1813   moreover
  1814   {assume "?c=0" hence ?case using zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1815       by (cases "?r", simp_all add: Let_def split_def, case_tac "nat", simp_all)}
  1816   moreover
  1817   {assume cp: "?c > 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (Eq a))" 
  1818       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1819     have "?I (Eq a) = (real (?c * i) + (?N ?r) = 0)" using Ia by (simp add: Let_def split_def)
  1820     also have "\<dots> = (?I (?l (Eq a)))" using cp cnz  by (simp only: split_int_eq_real'[where a="?c*i" and b="?N ?r"]) (simp add: Let_def split_def Ia real_of_int_mult[symmetric] del: real_of_int_mult)
  1821     finally have ?case using l by simp}
  1822   moreover
  1823   {assume cn: "?c < 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (Eq a))" 
  1824       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1825     have "?I (Eq a) = (real (?c * i) + (?N ?r) = 0)" using Ia by (simp add: Let_def split_def)
  1826     also from cn cnz have "\<dots> = (?I (?l (Eq a)))" by (simp only: split_int_eq_real'[where a="?c*i" and b="?N ?r"]) (simp add: Let_def split_def Ia real_of_int_mult[symmetric] del: real_of_int_mult,arith)
  1827     finally have ?case using l by simp}
  1828   ultimately show ?case by blast
  1829 next
  1830   case (10 a)
  1831   let ?c = "fst (zsplit0 a)"
  1832   let ?r = "snd (zsplit0 a)"
  1833   have spl: "zsplit0 a = (?c,?r)" by simp
  1834   from zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1835   have Ia:"Inum (real i # bs) a = Inum (real i #bs) (CN 0 ?c ?r)" and nb: "numbound0 ?r" by auto 
  1836   let ?N = "\<lambda> t. Inum (real i#bs) t"
  1837   have "?c = 0 \<or> (?c >0 \<and> ?c\<noteq>0) \<or> (?c<0 \<and> ?c\<noteq>0)" by arith
  1838   moreover
  1839   {assume "?c=0" hence ?case using zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1840       by (cases "?r", simp_all add: Let_def split_def, case_tac "nat", simp_all)}
  1841   moreover
  1842   {assume cp: "?c > 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (NEq a))" 
  1843       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1844     have "?I (NEq a) = (real (?c * i) + (?N ?r) \<noteq> 0)" using Ia by (simp add: Let_def split_def)
  1845     also have "\<dots> = (?I (?l (NEq a)))" using cp cnz  by (simp only: split_int_eq_real'[where a="?c*i" and b="?N ?r"]) (simp add: Let_def split_def Ia real_of_int_mult[symmetric] del: real_of_int_mult)
  1846     finally have ?case using l by simp}
  1847   moreover
  1848   {assume cn: "?c < 0" and cnz: "?c\<noteq>0" hence l: "?L (?l (NEq a))" 
  1849       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1850     have "?I (NEq a) = (real (?c * i) + (?N ?r) \<noteq> 0)" using Ia by (simp add: Let_def split_def)
  1851     also from cn cnz have "\<dots> = (?I (?l (NEq a)))" by (simp only: split_int_eq_real'[where a="?c*i" and b="?N ?r"]) (simp add: Let_def split_def Ia real_of_int_mult[symmetric] del: real_of_int_mult,arith)
  1852     finally have ?case using l by simp}
  1853   ultimately show ?case by blast
  1854 next
  1855   case (11 j a)
  1856   let ?c = "fst (zsplit0 a)"
  1857   let ?r = "snd (zsplit0 a)"
  1858   have spl: "zsplit0 a = (?c,?r)" by simp
  1859   from zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1860   have Ia:"Inum (real i # bs) a = Inum (real i #bs) (CN 0 ?c ?r)" and nb: "numbound0 ?r" by auto 
  1861   let ?N = "\<lambda> t. Inum (real i#bs) t"
  1862   have "j=0 \<or> (j\<noteq>0 \<and> ?c = 0) \<or> (j\<noteq>0 \<and> ?c >0 \<and> ?c\<noteq>0) \<or> (j\<noteq> 0 \<and> ?c<0 \<and> ?c\<noteq>0)" by arith
  1863   moreover
  1864   { assume j: "j=0" hence z: "zlfm (Dvd j a) = (zlfm (Eq a))" by (simp add: Let_def) 
  1865     hence ?case using 11 j by (simp del: zlfm.simps add: rdvd_left_0_eq)}
  1866   moreover
  1867   {assume "?c=0" and "j\<noteq>0" hence ?case 
  1868       using zsplit0_I[OF spl, where x="i" and bs="bs"] rdvd_abs1[where d="j"]
  1869       by (cases "?r", simp_all add: Let_def split_def, case_tac "nat", simp_all)}
  1870   moreover
  1871   {assume cp: "?c > 0" and cnz: "?c\<noteq>0" and jnz: "j\<noteq>0" hence l: "?L (?l (Dvd j a))" 
  1872       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1873     have "?I (Dvd j a) = (real j rdvd (real (?c * i) + (?N ?r)))" 
  1874       using Ia by (simp add: Let_def split_def)
  1875     also have "\<dots> = (real (abs j) rdvd real (?c*i) + (?N ?r))" 
  1876       by (simp only: rdvd_abs1[where d="j" and t="real (?c*i) + ?N ?r", symmetric]) simp
  1877     also have "\<dots> = ((abs j) dvd (floor ((?N ?r) + real (?c*i))) \<and> 
  1878        (real (floor ((?N ?r) + real (?c*i))) = (real (?c*i) + (?N ?r))))" 
  1879       by(simp only: int_rdvd_real[where i="abs j" and x="real (?c*i) + (?N ?r)"]) (simp only: add_ac)
  1880     also have "\<dots> = (?I (?l (Dvd j a)))" using cp cnz jnz  
  1881       by (simp add: Let_def split_def int_rdvd_iff[symmetric]  
  1882         del: real_of_int_mult) (auto simp add: add_ac)
  1883     finally have ?case using l jnz  by simp }
  1884   moreover
  1885   {assume cn: "?c < 0" and cnz: "?c\<noteq>0" and jnz: "j\<noteq>0" hence l: "?L (?l (Dvd j a))" 
  1886       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1887     have "?I (Dvd j a) = (real j rdvd (real (?c * i) + (?N ?r)))" 
  1888       using Ia by (simp add: Let_def split_def)
  1889     also have "\<dots> = (real (abs j) rdvd real (?c*i) + (?N ?r))" 
  1890       by (simp only: rdvd_abs1[where d="j" and t="real (?c*i) + ?N ?r", symmetric]) simp
  1891     also have "\<dots> = ((abs j) dvd (floor ((?N ?r) + real (?c*i))) \<and> 
  1892        (real (floor ((?N ?r) + real (?c*i))) = (real (?c*i) + (?N ?r))))" 
  1893       by(simp only: int_rdvd_real[where i="abs j" and x="real (?c*i) + (?N ?r)"]) (simp only: add_ac)
  1894     also have "\<dots> = (?I (?l (Dvd j a)))" using cn cnz jnz
  1895       using rdvd_minus [where d="abs j" and t="real (?c*i + floor (?N ?r))", simplified, symmetric]
  1896       by (simp add: Let_def split_def int_rdvd_iff[symmetric]  
  1897         del: real_of_int_mult) (auto simp add: add_ac)
  1898     finally have ?case using l jnz by blast }
  1899   ultimately show ?case by blast
  1900 next
  1901   case (12 j a)
  1902   let ?c = "fst (zsplit0 a)"
  1903   let ?r = "snd (zsplit0 a)"
  1904   have spl: "zsplit0 a = (?c,?r)" by simp
  1905   from zsplit0_I[OF spl, where x="i" and bs="bs"] 
  1906   have Ia:"Inum (real i # bs) a = Inum (real i #bs) (CN 0 ?c ?r)" and nb: "numbound0 ?r" by auto 
  1907   let ?N = "\<lambda> t. Inum (real i#bs) t"
  1908   have "j=0 \<or> (j\<noteq>0 \<and> ?c = 0) \<or> (j\<noteq>0 \<and> ?c >0 \<and> ?c\<noteq>0) \<or> (j\<noteq> 0 \<and> ?c<0 \<and> ?c\<noteq>0)" by arith
  1909   moreover
  1910   {assume j: "j=0" hence z: "zlfm (NDvd j a) = (zlfm (NEq a))" by (simp add: Let_def) 
  1911     hence ?case using 12 j by (simp del: zlfm.simps add: rdvd_left_0_eq)}
  1912   moreover
  1913   {assume "?c=0" and "j\<noteq>0" hence ?case 
  1914       using zsplit0_I[OF spl, where x="i" and bs="bs"] rdvd_abs1[where d="j"]
  1915       by (cases "?r", simp_all add: Let_def split_def, case_tac "nat", simp_all)}
  1916   moreover
  1917   {assume cp: "?c > 0" and cnz: "?c\<noteq>0" and jnz: "j\<noteq>0" hence l: "?L (?l (NDvd j a))" 
  1918       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1919     have "?I (NDvd j a) = (\<not> (real j rdvd (real (?c * i) + (?N ?r))))" 
  1920       using Ia by (simp add: Let_def split_def)
  1921     also have "\<dots> = (\<not> (real (abs j) rdvd real (?c*i) + (?N ?r)))" 
  1922       by (simp only: rdvd_abs1[where d="j" and t="real (?c*i) + ?N ?r", symmetric]) simp
  1923     also have "\<dots> = (\<not> ((abs j) dvd (floor ((?N ?r) + real (?c*i))) \<and> 
  1924        (real (floor ((?N ?r) + real (?c*i))) = (real (?c*i) + (?N ?r)))))" 
  1925       by(simp only: int_rdvd_real[where i="abs j" and x="real (?c*i) + (?N ?r)"]) (simp only: add_ac)
  1926     also have "\<dots> = (?I (?l (NDvd j a)))" using cp cnz jnz  
  1927       by (simp add: Let_def split_def int_rdvd_iff[symmetric]  
  1928         del: real_of_int_mult) (auto simp add: add_ac)
  1929     finally have ?case using l jnz  by simp }
  1930   moreover
  1931   {assume cn: "?c < 0" and cnz: "?c\<noteq>0" and jnz: "j\<noteq>0" hence l: "?L (?l (NDvd j a))" 
  1932       by (simp add: nb Let_def split_def isint_Floor isint_neg)
  1933     have "?I (NDvd j a) = (\<not> (real j rdvd (real (?c * i) + (?N ?r))))" 
  1934       using Ia by (simp add: Let_def split_def)
  1935     also have "\<dots> = (\<not> (real (abs j) rdvd real (?c*i) + (?N ?r)))" 
  1936       by (simp only: rdvd_abs1[where d="j" and t="real (?c*i) + ?N ?r", symmetric]) simp
  1937     also have "\<dots> = (\<not> ((abs j) dvd (floor ((?N ?r) + real (?c*i))) \<and> 
  1938        (real (floor ((?N ?r) + real (?c*i))) = (real (?c*i) + (?N ?r)))))" 
  1939       by(simp only: int_rdvd_real[where i="abs j" and x="real (?c*i) + (?N ?r)"]) (simp only: add_ac)
  1940     also have "\<dots> = (?I (?l (NDvd j a)))" using cn cnz jnz
  1941       using rdvd_minus [where d="abs j" and t="real (?c*i + floor (?N ?r))", simplified, symmetric]
  1942       by (simp add: Let_def split_def int_rdvd_iff[symmetric]  
  1943         del: real_of_int_mult) (auto simp add: add_ac)
  1944     finally have ?case using l jnz by blast }
  1945   ultimately show ?case by blast
  1946 qed auto
  1947 
  1948 text{* plusinf : Virtual substitution of @{text "+\<infinity>"}
  1949        minusinf: Virtual substitution of @{text "-\<infinity>"}
  1950        @{text "\<delta>"} Compute lcm @{text "d| Dvd d  c*x+t \<in> p"}
  1951        @{text "d\<delta>"} checks if a given l divides all the ds above*}
  1952 
  1953 fun minusinf:: "fm \<Rightarrow> fm" where
  1954   "minusinf (And p q) = conj (minusinf p) (minusinf q)" 
  1955 | "minusinf (Or p q) = disj (minusinf p) (minusinf q)" 
  1956 | "minusinf (Eq  (CN 0 c e)) = F"
  1957 | "minusinf (NEq (CN 0 c e)) = T"
  1958 | "minusinf (Lt  (CN 0 c e)) = T"
  1959 | "minusinf (Le  (CN 0 c e)) = T"
  1960 | "minusinf (Gt  (CN 0 c e)) = F"
  1961 | "minusinf (Ge  (CN 0 c e)) = F"
  1962 | "minusinf p = p"
  1963 
  1964 lemma minusinf_qfree: "qfree p \<Longrightarrow> qfree (minusinf p)"
  1965   by (induct p rule: minusinf.induct, auto)
  1966 
  1967 fun plusinf:: "fm \<Rightarrow> fm" where
  1968   "plusinf (And p q) = conj (plusinf p) (plusinf q)" 
  1969 | "plusinf (Or p q) = disj (plusinf p) (plusinf q)" 
  1970 | "plusinf (Eq  (CN 0 c e)) = F"
  1971 | "plusinf (NEq (CN 0 c e)) = T"
  1972 | "plusinf (Lt  (CN 0 c e)) = F"
  1973 | "plusinf (Le  (CN 0 c e)) = F"
  1974 | "plusinf (Gt  (CN 0 c e)) = T"
  1975 | "plusinf (Ge  (CN 0 c e)) = T"
  1976 | "plusinf p = p"
  1977 
  1978 fun \<delta> :: "fm \<Rightarrow> int" where
  1979   "\<delta> (And p q) = lcm (\<delta> p) (\<delta> q)" 
  1980 | "\<delta> (Or p q) = lcm (\<delta> p) (\<delta> q)" 
  1981 | "\<delta> (Dvd i (CN 0 c e)) = i"
  1982 | "\<delta> (NDvd i (CN 0 c e)) = i"
  1983 | "\<delta> p = 1"
  1984 
  1985 fun d\<delta> :: "fm \<Rightarrow> int \<Rightarrow> bool" where
  1986   "d\<delta> (And p q) = (\<lambda> d. d\<delta> p d \<and> d\<delta> q d)" 
  1987 | "d\<delta> (Or p q) = (\<lambda> d. d\<delta> p d \<and> d\<delta> q d)" 
  1988 | "d\<delta> (Dvd i (CN 0 c e)) = (\<lambda> d. i dvd d)"
  1989 | "d\<delta> (NDvd i (CN 0 c e)) = (\<lambda> d. i dvd d)"
  1990 | "d\<delta> p = (\<lambda> d. True)"
  1991 
  1992 lemma delta_mono: 
  1993   assumes lin: "iszlfm p bs"
  1994   and d: "d dvd d'"
  1995   and ad: "d\<delta> p d"
  1996   shows "d\<delta> p d'"
  1997   using lin ad d
  1998 proof(induct p rule: iszlfm.induct)
  1999   case (9 i c e)  thus ?case using d
  2000     by (simp add: dvd_trans[of "i" "d" "d'"])
  2001 next
  2002   case (10 i c e) thus ?case using d
  2003     by (simp add: dvd_trans[of "i" "d" "d'"])
  2004 qed simp_all
  2005 
  2006 lemma \<delta> : assumes lin:"iszlfm p bs"
  2007   shows "d\<delta> p (\<delta> p) \<and> \<delta> p >0"
  2008 using lin
  2009 proof (induct p rule: iszlfm.induct)
  2010   case (1 p q) 
  2011   let ?d = "\<delta> (And p q)"
  2012   from 1 lcm_pos_int have dp: "?d >0" by simp
  2013   have d1: "\<delta> p dvd \<delta> (And p q)" using 1 by simp 
  2014   hence th: "d\<delta> p ?d" 
  2015     using delta_mono 1 by (simp only: iszlfm.simps) blast
  2016   have "\<delta> q dvd \<delta> (And p q)" using 1 by simp 
  2017   hence th': "d\<delta> q ?d" using delta_mono 1 by (simp only: iszlfm.simps) blast
  2018   from th th' dp show ?case by simp 
  2019 next
  2020   case (2 p q)  
  2021   let ?d = "\<delta> (And p q)"
  2022   from 2 lcm_pos_int have dp: "?d >0" by simp
  2023   have "\<delta> p dvd \<delta> (And p q)" using 2 by simp
  2024   hence th: "d\<delta> p ?d" using delta_mono 2 by (simp only: iszlfm.simps) blast
  2025   have "\<delta> q dvd \<delta> (And p q)" using 2 by simp
  2026   hence th': "d\<delta> q ?d" using delta_mono 2 by (simp only: iszlfm.simps) blast
  2027   from th th' dp show ?case by simp
  2028 qed simp_all
  2029 
  2030 
  2031 lemma minusinf_inf:
  2032   assumes linp: "iszlfm p (a # bs)"
  2033   shows "\<exists> (z::int). \<forall> x < z. Ifm ((real x)#bs) (minusinf p) = Ifm ((real x)#bs) p"
  2034   (is "?P p" is "\<exists> (z::int). \<forall> x < z. ?I x (?M p) = ?I x p")
  2035 using linp
  2036 proof (induct p rule: minusinf.induct)
  2037   case (1 f g)
  2038   then have "?P f" by simp
  2039   then obtain z1 where z1_def: "\<forall> x < z1. ?I x (?M f) = ?I x f" by blast
  2040   with 1 have "?P g" by simp
  2041   then obtain z2 where z2_def: "\<forall> x < z2. ?I x (?M g) = ?I x g" by blast
  2042   let ?z = "min z1 z2"
  2043   from z1_def z2_def have "\<forall> x < ?z. ?I x (?M (And f g)) = ?I x (And f g)" by simp
  2044   thus ?case by blast
  2045 next
  2046   case (2 f g)
  2047   then have "?P f" by simp
  2048   then obtain z1 where z1_def: "\<forall> x < z1. ?I x (?M f) = ?I x f" by blast
  2049   with 2 have "?P g" by simp
  2050   then obtain z2 where z2_def: "\<forall> x < z2. ?I x (?M g) = ?I x g" by blast
  2051   let ?z = "min z1 z2"
  2052   from z1_def z2_def have "\<forall> x < ?z. ?I x (?M (Or f g)) = ?I x (Or f g)" by simp
  2053   thus ?case by blast
  2054 next
  2055   case (3 c e) 
  2056   then have "c > 0" by simp
  2057   hence rcpos: "real c > 0" by simp
  2058   from 3 have nbe: "numbound0 e" by simp
  2059   fix y
  2060   have "\<forall> x < (floor (- (Inum (y#bs) e) / (real c))). ?I x (?M (Eq (CN 0 c e))) = ?I x (Eq (CN 0 c e))"
  2061   proof (simp add: less_floor_eq , rule allI, rule impI) 
  2062     fix x
  2063     assume A: "real x + (1\<Colon>real) \<le> - (Inum (y # bs) e / real c)"
  2064     hence th1:"real x < - (Inum (y # bs) e / real c)" by simp
  2065     with rcpos  have "(real c)*(real  x) < (real c)*(- (Inum (y # bs) e / real c))"
  2066       by (simp only: mult_strict_left_mono [OF th1 rcpos])
  2067     hence "real c * real x + Inum (y # bs) e \<noteq> 0"using rcpos  by simp
  2068     thus "real c * real x + Inum (real x # bs) e \<noteq> 0" 
  2069       using numbound0_I[OF nbe, where b="y" and bs="bs" and b'="real x"]  by simp
  2070   qed
  2071   thus ?case by blast
  2072 next
  2073   case (4 c e) 
  2074   then have "c > 0" by simp hence rcpos: "real c > 0" by simp
  2075   from 4 have nbe: "numbound0 e" by simp
  2076   fix y
  2077   have "\<forall> x < (floor (- (Inum (y#bs) e) / (real c))). ?I x (?M (NEq (CN 0 c e))) = ?I x (NEq (CN 0 c e))"
  2078   proof (simp add: less_floor_eq , rule allI, rule impI) 
  2079     fix x
  2080     assume A: "real x + (1\<Colon>real) \<le> - (Inum (y # bs) e / real c)"
  2081     hence th1:"real x < - (Inum (y # bs) e / real c)" by simp
  2082     with rcpos  have "(real c)*(real  x) < (real c)*(- (Inum (y # bs) e / real c))"
  2083       by (simp only: mult_strict_left_mono [OF th1 rcpos])
  2084     hence "real c * real x + Inum (y # bs) e \<noteq> 0"using rcpos  by simp
  2085     thus "real c * real x + Inum (real x # bs) e \<noteq> 0" 
  2086       using numbound0_I[OF nbe, where b="y" and bs="bs" and b'="real x"]  by simp
  2087   qed
  2088   thus ?case by blast
  2089 next
  2090   case (5 c e) 
  2091   then have "c > 0" by simp hence rcpos: "real c > 0" by simp
  2092   from 5 have nbe: "numbound0 e" by simp
  2093   fix y
  2094   have "\<forall> x < (floor (- (Inum (y#bs) e) / (real c))). ?I x (?M (Lt (CN 0 c e))) = ?I x (Lt (CN 0 c e))"
  2095   proof (simp add: less_floor_eq , rule allI, rule impI) 
  2096     fix x
  2097     assume A: "real x + (1\<Colon>real) \<le> - (Inum (y # bs) e / real c)"
  2098     hence th1:"real x < - (Inum (y # bs) e / real c)" by simp
  2099     with rcpos  have "(real c)*(real  x) < (real c)*(- (Inum (y # bs) e / real c))"
  2100       by (simp only: mult_strict_left_mono [OF th1 rcpos])
  2101     thus "real c * real x + Inum (real x # bs) e < 0" 
  2102       using numbound0_I[OF nbe, where b="y" and bs="bs" and b'="real x"] rcpos by simp
  2103   qed
  2104   thus ?case by blast
  2105 next
  2106   case (6 c e) 
  2107   then have "c > 0" by simp hence rcpos: "real c > 0" by simp
  2108   from 6 have nbe: "numbound0 e" by simp
  2109   fix y
  2110   have "\<forall> x < (floor (- (Inum (y#bs) e) / (real c))). ?I x (?M (Le (CN 0 c e))) = ?I x (Le (CN 0 c e))"
  2111   proof (simp add: less_floor_eq , rule allI, rule impI) 
  2112     fix x
  2113     assume A: "real x + (1\<Colon>real) \<le> - (Inum (y # bs) e / real c)"
  2114     hence th1:"real x < - (Inum (y # bs) e / real c)" by simp
  2115     with rcpos  have "(real c)*(real  x) < (real c)*(- (Inum (y # bs) e / real c))"
  2116       by (simp only: mult_strict_left_mono [OF th1 rcpos])
  2117     thus "real c * real x + Inum (real x # bs) e \<le> 0" 
  2118       using numbound0_I[OF nbe, where b="y" and bs="bs" and b'="real x"] rcpos by simp
  2119   qed
  2120   thus ?case by blast
  2121 next
  2122   case (7 c e) 
  2123   then have "c > 0" by simp hence rcpos: "real c > 0" by simp
  2124   from 7 have nbe: "numbound0 e" by simp
  2125   fix y
  2126   have "\<forall> x < (floor (- (Inum (y#bs) e) / (real c))). ?I x (?M (Gt (CN 0 c e))) = ?I x (Gt (CN 0 c e))"
  2127   proof (simp add: less_floor_eq , rule allI, rule impI) 
  2128     fix x
  2129     assume A: "real x + (1\<Colon>real) \<le> - (Inum (y # bs) e / real c)"
  2130     hence th1:"real x < - (Inum (y # bs) e / real c)" by simp
  2131     with rcpos  have "(real c)*(real  x) < (real c)*(- (Inum (y # bs) e / real c))"
  2132       by (simp only: mult_strict_left_mono [OF th1 rcpos])
  2133     thus "\<not> (real c * real x + Inum (real x # bs) e>0)" 
  2134       using numbound0_I[OF nbe, where b="y" and bs="bs" and b'="real x"] rcpos by simp
  2135   qed
  2136   thus ?case by blast
  2137 next
  2138   case (8 c e) 
  2139   then have "c > 0" by simp hence rcpos: "real c > 0" by simp
  2140   from 8 have nbe: "numbound0 e" by simp
  2141   fix y
  2142   have "\<forall> x < (floor (- (Inum (y#bs) e) / (real c))). ?I x (?M (Ge (CN 0 c e))) = ?I x (Ge (CN 0 c e))"
  2143   proof (simp add: less_floor_eq , rule allI, rule impI) 
  2144     fix x
  2145     assume A: "real x + (1\<Colon>real) \<le> - (Inum (y # bs) e / real c)"
  2146     hence th1:"real x < - (Inum (y # bs) e / real c)" by simp
  2147     with rcpos  have "(real c)*(real  x) < (real c)*(- (Inum (y # bs) e / real c))"
  2148       by (simp only: mult_strict_left_mono [OF th1 rcpos])
  2149     thus "\<not> real c * real x + Inum (real x # bs) e \<ge> 0" 
  2150       using numbound0_I[OF nbe, where b="y" and bs="bs" and b'="real x"] rcpos by simp
  2151   qed
  2152   thus ?case by blast
  2153 qed simp_all
  2154 
  2155 lemma minusinf_repeats:
  2156   assumes d: "d\<delta> p d" and linp: "iszlfm p (a # bs)"
  2157   shows "Ifm ((real(x - k*d))#bs) (minusinf p) = Ifm (real x #bs) (minusinf p)"
  2158 using linp d
  2159 proof(induct p rule: iszlfm.induct) 
  2160   case (9 i c e) hence nbe: "numbound0 e"  and id: "i dvd d" by simp+
  2161     hence "\<exists> k. d=i*k" by (simp add: dvd_def)
  2162     then obtain "di" where di_def: "d=i*di" by blast
  2163     show ?case 
  2164     proof(simp add: numbound0_I[OF nbe,where bs="bs" and b="real x - real k * real d" and b'="real x"] right_diff_distrib, rule iffI)
  2165       assume 
  2166         "real i rdvd real c * real x - real c * (real k * real d) + Inum (real x # bs) e"
  2167       (is "?ri rdvd ?rc*?rx - ?rc*(?rk*?rd) + ?I x e" is "?ri rdvd ?rt")
  2168       hence "\<exists> (l::int). ?rt = ?ri * (real l)" by (simp add: rdvd_def)
  2169       hence "\<exists> (l::int). ?rc*?rx+ ?I x e = ?ri*(real l)+?rc*(?rk * (real i) * (real di))" 
  2170         by (simp add: algebra_simps di_def)
  2171       hence "\<exists> (l::int). ?rc*?rx+ ?I x e = ?ri*(real (l + c*k*di))"
  2172         by (simp add: algebra_simps)
  2173       hence "\<exists> (l::int). ?rc*?rx+ ?I x e = ?ri* (real l)" by blast
  2174       thus "real i rdvd real c * real x + Inum (real x # bs) e" using rdvd_def by simp
  2175     next
  2176       assume 
  2177         "real i rdvd real c * real x + Inum (real x # bs) e" (is "?ri rdvd ?rc*?rx+?e")
  2178       hence "\<exists> (l::int). ?rc*?rx+?e = ?ri * (real l)" by (simp add: rdvd_def)
  2179       hence "\<exists> (l::int). ?rc*?rx - real c * (real k * real d) +?e = ?ri * (real l) - real c * (real k * real d)" by simp
  2180       hence "\<exists> (l::int). ?rc*?rx - real c * (real k * real d) +?e = ?ri * (real l) - real c * (real k * real i * real di)" by (simp add: di_def)
  2181       hence "\<exists> (l::int). ?rc*?rx - real c * (real k * real d) +?e = ?ri * (real (l - c*k*di))" by (simp add: algebra_simps)
  2182       hence "\<exists> (l::int). ?rc*?rx - real c * (real k * real d) +?e = ?ri * (real l)"
  2183         by blast
  2184       thus "real i rdvd real c * real x - real c * (real k * real d) + Inum (real x # bs) e" using rdvd_def by simp
  2185     qed
  2186 next
  2187   case (10 i c e) hence nbe: "numbound0 e"  and id: "i dvd d" by simp+
  2188     hence "\<exists> k. d=i*k" by (simp add: dvd_def)
  2189     then obtain "di" where di_def: "d=i*di" by blast
  2190     show ?case 
  2191     proof(simp add: numbound0_I[OF nbe,where bs="bs" and b="real x - real k * real d" and b'="real x"] right_diff_distrib, rule iffI)
  2192       assume 
  2193         "real i rdvd real c * real x - real c * (real k * real d) + Inum (real x # bs) e"
  2194       (is "?ri rdvd ?rc*?rx - ?rc*(?rk*?rd) + ?I x e" is "?ri rdvd ?rt")
  2195       hence "\<exists> (l::int). ?rt = ?ri * (real l)" by (simp add: rdvd_def)
  2196       hence "\<exists> (l::int). ?rc*?rx+ ?I x e = ?ri*(real l)+?rc*(?rk * (real i) * (real di))" 
  2197         by (simp add: algebra_simps di_def)
  2198       hence "\<exists> (l::int). ?rc*?rx+ ?I x e = ?ri*(real (l + c*k*di))"
  2199         by (simp add: algebra_simps)
  2200       hence "\<exists> (l::int). ?rc*?rx+ ?I x e = ?ri* (real l)" by blast
  2201       thus "real i rdvd real c * real x + Inum (real x # bs) e" using rdvd_def by simp
  2202     next
  2203       assume 
  2204         "real i rdvd real c * real x + Inum (real x # bs) e" (is "?ri rdvd ?rc*?rx+?e")
  2205       hence "\<exists> (l::int). ?rc*?rx+?e = ?ri * (real l)" by (simp add: rdvd_def)
  2206       hence "\<exists> (l::int). ?rc*?rx - real c * (real k * real d) +?e = ?ri * (real l) - real c * (real k * real d)" by simp
  2207       hence "\<exists> (l::int). ?rc*?rx - real c * (real k * real d) +?e = ?ri * (real l) - real c * (real k * real i * real di)" by (simp add: di_def)
  2208       hence "\<exists> (l::int). ?rc*?rx - real c * (real k * real d) +?e = ?ri * (real (l - c*k*di))" by (simp add: algebra_simps)
  2209       hence "\<exists> (l::int). ?rc*?rx - real c * (real k * real d) +?e = ?ri * (real l)"
  2210         by blast
  2211       thus "real i rdvd real c * real x - real c * (real k * real d) + Inum (real x # bs) e" using rdvd_def by simp
  2212     qed
  2213 qed (auto simp add: numbound0_I[where bs="bs" and b="real(x - k*d)" and b'="real x"] simp del: real_of_int_mult real_of_int_diff)
  2214 
  2215 lemma minusinf_ex:
  2216   assumes lin: "iszlfm p (real (a::int) #bs)"
  2217   and exmi: "\<exists> (x::int). Ifm (real x#bs) (minusinf p)" (is "\<exists> x. ?P1 x")
  2218   shows "\<exists> (x::int). Ifm (real x#bs) p" (is "\<exists> x. ?P x")
  2219 proof-
  2220   let ?d = "\<delta> p"
  2221   from \<delta> [OF lin] have dpos: "?d >0" by simp
  2222   from \<delta> [OF lin] have alld: "d\<delta> p ?d" by simp
  2223   from minusinf_repeats[OF alld lin] have th1:"\<forall> x k. ?P1 x = ?P1 (x - (k * ?d))" by simp
  2224   from minusinf_inf[OF lin] have th2:"\<exists> z. \<forall> x. x<z \<longrightarrow> (?P x = ?P1 x)" by blast
  2225   from minusinfinity [OF dpos th1 th2] exmi show ?thesis by blast
  2226 qed
  2227 
  2228 lemma minusinf_bex:
  2229   assumes lin: "iszlfm p (real (a::int) #bs)"
  2230   shows "(\<exists> (x::int). Ifm (real x#bs) (minusinf p)) = 
  2231          (\<exists> (x::int)\<in> {1..\<delta> p}. Ifm (real x#bs) (minusinf p))"
  2232   (is "(\<exists> x. ?P x) = _")
  2233 proof-
  2234   let ?d = "\<delta> p"
  2235   from \<delta> [OF lin] have dpos: "?d >0" by simp
  2236   from \<delta> [OF lin] have alld: "d\<delta> p ?d" by simp
  2237   from minusinf_repeats[OF alld lin] have th1:"\<forall> x k. ?P x = ?P (x - (k * ?d))" by simp
  2238   from periodic_finite_ex[OF dpos th1] show ?thesis by blast
  2239 qed
  2240 
  2241 lemma dvd1_eq1: "x >0 \<Longrightarrow> (x::int) dvd 1 = (x = 1)" by auto
  2242 
  2243 consts 
  2244   a\<beta> :: "fm \<Rightarrow> int \<Rightarrow> fm" (* adjusts the coeffitients of a formula *)
  2245   d\<beta> :: "fm \<Rightarrow> int \<Rightarrow> bool" (* tests if all coeffs c of c divide a given l*)
  2246   \<zeta>  :: "fm \<Rightarrow> int" (* computes the lcm of all coefficients of x*)
  2247   \<beta> :: "fm \<Rightarrow> num list"
  2248   \<alpha> :: "fm \<Rightarrow> num list"
  2249 
  2250 recdef a\<beta> "measure size"
  2251   "a\<beta> (And p q) = (\<lambda> k. And (a\<beta> p k) (a\<beta> q k))" 
  2252   "a\<beta> (Or p q) = (\<lambda> k. Or (a\<beta> p k) (a\<beta> q k))" 
  2253   "a\<beta> (Eq  (CN 0 c e)) = (\<lambda> k. Eq (CN 0 1 (Mul (k div c) e)))"
  2254   "a\<beta> (NEq (CN 0 c e)) = (\<lambda> k. NEq (CN 0 1 (Mul (k div c) e)))"
  2255   "a\<beta> (Lt  (CN 0 c e)) = (\<lambda> k. Lt (CN 0 1 (Mul (k div c) e)))"
  2256   "a\<beta> (Le  (CN 0 c e)) = (\<lambda> k. Le (CN 0 1 (Mul (k div c) e)))"
  2257   "a\<beta> (Gt  (CN 0 c e)) = (\<lambda> k. Gt (CN 0 1 (Mul (k div c) e)))"
  2258   "a\<beta> (Ge  (CN 0 c e)) = (\<lambda> k. Ge (CN 0 1 (Mul (k div c) e)))"
  2259   "a\<beta> (Dvd i (CN 0 c e)) =(\<lambda> k. Dvd ((k div c)*i) (CN 0 1 (Mul (k div c) e)))"
  2260   "a\<beta> (NDvd i (CN 0 c e))=(\<lambda> k. NDvd ((k div c)*i) (CN 0 1 (Mul (k div c) e)))"
  2261   "a\<beta> p = (\<lambda> k. p)"
  2262 
  2263 recdef d\<beta> "measure size"
  2264   "d\<beta> (And p q) = (\<lambda> k. (d\<beta> p k) \<and> (d\<beta> q k))" 
  2265   "d\<beta> (Or p q) = (\<lambda> k. (d\<beta> p k) \<and> (d\<beta> q k))" 
  2266   "d\<beta> (Eq  (CN 0 c e)) = (\<lambda> k. c dvd k)"
  2267   "d\<beta> (NEq (CN 0 c e)) = (\<lambda> k. c dvd k)"
  2268   "d\<beta> (Lt  (CN 0 c e)) = (\<lambda> k. c dvd k)"
  2269   "d\<beta> (Le  (CN 0 c e)) = (\<lambda> k. c dvd k)"
  2270   "d\<beta> (Gt  (CN 0 c e)) = (\<lambda> k. c dvd k)"
  2271   "d\<beta> (Ge  (CN 0 c e)) = (\<lambda> k. c dvd k)"
  2272   "d\<beta> (Dvd i (CN 0 c e)) =(\<lambda> k. c dvd k)"
  2273   "d\<beta> (NDvd i (CN 0 c e))=(\<lambda> k. c dvd k)"
  2274   "d\<beta> p = (\<lambda> k. True)"
  2275 
  2276 recdef \<zeta> "measure size"
  2277   "\<zeta> (And p q) = lcm (\<zeta> p) (\<zeta> q)" 
  2278   "\<zeta> (Or p q) = lcm (\<zeta> p) (\<zeta> q)" 
  2279   "\<zeta> (Eq  (CN 0 c e)) = c"
  2280   "\<zeta> (NEq (CN 0 c e)) = c"
  2281   "\<zeta> (Lt  (CN 0 c e)) = c"
  2282   "\<zeta> (Le  (CN 0 c e)) = c"
  2283   "\<zeta> (Gt  (CN 0 c e)) = c"
  2284   "\<zeta> (Ge  (CN 0 c e)) = c"
  2285   "\<zeta> (Dvd i (CN 0 c e)) = c"
  2286   "\<zeta> (NDvd i (CN 0 c e))= c"
  2287   "\<zeta> p = 1"
  2288 
  2289 recdef \<beta> "measure size"
  2290   "\<beta> (And p q) = (\<beta> p @ \<beta> q)" 
  2291   "\<beta> (Or p q) = (\<beta> p @ \<beta> q)" 
  2292   "\<beta> (Eq  (CN 0 c e)) = [Sub (C -1) e]"
  2293   "\<beta> (NEq (CN 0 c e)) = [Neg e]"
  2294   "\<beta> (Lt  (CN 0 c e)) = []"
  2295   "\<beta> (Le  (CN 0 c e)) = []"
  2296   "\<beta> (Gt  (CN 0 c e)) = [Neg e]"
  2297   "\<beta> (Ge  (CN 0 c e)) = [Sub (C -1) e]"
  2298   "\<beta> p = []"
  2299 
  2300 recdef \<alpha> "measure size"
  2301   "\<alpha> (And p q) = (\<alpha> p @ \<alpha> q)" 
  2302   "\<alpha> (Or p q) = (\<alpha> p @ \<alpha> q)" 
  2303   "\<alpha> (Eq  (CN 0 c e)) = [Add (C -1) e]"
  2304   "\<alpha> (NEq (CN 0 c e)) = [e]"
  2305   "\<alpha> (Lt  (CN 0 c e)) = [e]"
  2306   "\<alpha> (Le  (CN 0 c e)) = [Add (C -1) e]"
  2307   "\<alpha> (Gt  (CN 0 c e)) = []"
  2308   "\<alpha> (Ge  (CN 0 c e)) = []"
  2309   "\<alpha> p = []"
  2310 consts mirror :: "fm \<Rightarrow> fm"
  2311 recdef mirror "measure size"
  2312   "mirror (And p q) = And (mirror p) (mirror q)" 
  2313   "mirror (Or p q) = Or (mirror p) (mirror q)" 
  2314   "mirror (Eq  (CN 0 c e)) = Eq (CN 0 c (Neg e))"
  2315   "mirror (NEq (CN 0 c e)) = NEq (CN 0 c (Neg e))"
  2316   "mirror (Lt  (CN 0 c e)) = Gt (CN 0 c (Neg e))"
  2317   "mirror (Le  (CN 0 c e)) = Ge (CN 0 c (Neg e))"
  2318   "mirror (Gt  (CN 0 c e)) = Lt (CN 0 c (Neg e))"
  2319   "mirror (Ge  (CN 0 c e)) = Le (CN 0 c (Neg e))"
  2320   "mirror (Dvd i (CN 0 c e)) = Dvd i (CN 0 c (Neg e))"
  2321   "mirror (NDvd i (CN 0 c e)) = NDvd i (CN 0 c (Neg e))"
  2322   "mirror p = p"
  2323 
  2324 lemma mirror\<alpha>\<beta>:
  2325   assumes lp: "iszlfm p (a#bs)"
  2326   shows "(Inum (real (i::int)#bs)) ` set (\<alpha> p) = (Inum (real i#bs)) ` set (\<beta> (mirror p))"
  2327 using lp
  2328 by (induct p rule: mirror.induct, auto)
  2329 
  2330 lemma mirror: 
  2331   assumes lp: "iszlfm p (a#bs)"
  2332   shows "Ifm (real (x::int)#bs) (mirror p) = Ifm (real (- x)#bs) p" 
  2333 using lp
  2334 proof(induct p rule: iszlfm.induct)
  2335   case (9 j c e)
  2336   have th: "(real j rdvd real c * real x - Inum (real x # bs) e) =
  2337        (real j rdvd - (real c * real x - Inum (real x # bs) e))"
  2338     by (simp only: rdvd_minus[symmetric])
  2339   from 9 th show ?case
  2340     by (simp add: algebra_simps
  2341       numbound0_I[where bs="bs" and b'="real x" and b="- real x"])
  2342 next
  2343   case (10 j c e)
  2344   have th: "(real j rdvd real c * real x - Inum (real x # bs) e) =
  2345        (real j rdvd - (real c * real x - Inum (real x # bs) e))"
  2346     by (simp only: rdvd_minus[symmetric])
  2347   from 10 th show  ?case
  2348     by (simp add: algebra_simps
  2349       numbound0_I[where bs="bs" and b'="real x" and b="- real x"])
  2350 qed (auto simp add: numbound0_I[where bs="bs" and b="real x" and b'="- real x"])
  2351 
  2352 lemma mirror_l: "iszlfm p (a#bs) \<Longrightarrow> iszlfm (mirror p) (a#bs)"
  2353 by (induct p rule: mirror.induct, auto simp add: isint_neg)
  2354 
  2355 lemma mirror_d\<beta>: "iszlfm p (a#bs) \<and> d\<beta> p 1 
  2356   \<Longrightarrow> iszlfm (mirror p) (a#bs) \<and> d\<beta> (mirror p) 1"
  2357 by (induct p rule: mirror.induct, auto simp add: isint_neg)
  2358 
  2359 lemma mirror_\<delta>: "iszlfm p (a#bs) \<Longrightarrow> \<delta> (mirror p) = \<delta> p"
  2360 by (induct p rule: mirror.induct,auto)
  2361 
  2362 
  2363 lemma mirror_ex: 
  2364   assumes lp: "iszlfm p (real (i::int)#bs)"
  2365   shows "(\<exists> (x::int). Ifm (real x#bs) (mirror p)) = (\<exists> (x::int). Ifm (real x#bs) p)"
  2366   (is "(\<exists> x. ?I x ?mp) = (\<exists> x. ?I x p)")
  2367 proof(auto)
  2368   fix x assume "?I x ?mp" hence "?I (- x) p" using mirror[OF lp] by blast
  2369   thus "\<exists> x. ?I x p" by blast
  2370 next
  2371   fix x assume "?I x p" hence "?I (- x) ?mp" 
  2372     using mirror[OF lp, where x="- x", symmetric] by auto
  2373   thus "\<exists> x. ?I x ?mp" by blast
  2374 qed
  2375 
  2376 lemma \<beta>_numbound0: assumes lp: "iszlfm p bs"
  2377   shows "\<forall> b\<in> set (\<beta> p). numbound0 b"
  2378   using lp by (induct p rule: \<beta>.induct,auto)
  2379 
  2380 lemma d\<beta>_mono: 
  2381   assumes linp: "iszlfm p (a #bs)"
  2382   and dr: "d\<beta> p l"
  2383   and d: "l dvd l'"
  2384   shows "d\<beta> p l'"
  2385 using dr linp dvd_trans[of _ "l" "l'", simplified d]
  2386 by (induct p rule: iszlfm.induct) simp_all
  2387 
  2388 lemma \<alpha>_l: assumes lp: "iszlfm p (a#bs)"
  2389   shows "\<forall> b\<in> set (\<alpha> p). numbound0 b \<and> isint b (a#bs)"
  2390 using lp
  2391 by(induct p rule: \<alpha>.induct, auto simp add: isint_add isint_c)
  2392 
  2393 lemma \<zeta>: 
  2394   assumes linp: "iszlfm p (a #bs)"
  2395   shows "\<zeta> p > 0 \<and> d\<beta> p (\<zeta> p)"
  2396 using linp
  2397 proof(induct p rule: iszlfm.induct)
  2398   case (1 p q)
  2399   then  have dl1: "\<zeta> p dvd lcm (\<zeta> p) (\<zeta> q)" by simp
  2400   from 1 have dl2: "\<zeta> q dvd lcm (\<zeta> p) (\<zeta> q)" by simp
  2401   from 1 d\<beta>_mono[where p = "p" and l="\<zeta> p" and l'="lcm (\<zeta> p) (\<zeta> q)"] 
  2402     d\<beta>_mono[where p = "q" and l="\<zeta> q" and l'="lcm (\<zeta> p) (\<zeta> q)"] 
  2403     dl1 dl2 show ?case by (auto simp add: lcm_pos_int)
  2404 next
  2405   case (2 p q)
  2406   then have dl1: "\<zeta> p dvd lcm (\<zeta> p) (\<zeta> q)" by simp
  2407   from 2 have dl2: "\<zeta> q dvd lcm (\<zeta> p) (\<zeta> q)" by simp
  2408   from 2 d\<beta>_mono[where p = "p" and l="\<zeta> p" and l'="lcm (\<zeta> p) (\<zeta> q)"] 
  2409     d\<beta>_mono[where p = "q" and l="\<zeta> q" and l'="lcm (\<zeta> p) (\<zeta> q)"] 
  2410     dl1 dl2 show ?case by (auto simp add: lcm_pos_int)
  2411 qed (auto simp add: lcm_pos_int)
  2412 
  2413 lemma a\<beta>: assumes linp: "iszlfm p (a #bs)" and d: "d\<beta> p l" and lp: "l > 0"
  2414   shows "iszlfm (a\<beta> p l) (a #bs) \<and> d\<beta> (a\<beta> p l) 1 \<and> (Ifm (real (l * x) #bs) (a\<beta> p l) = Ifm ((real x)#bs) p)"
  2415 using linp d
  2416 proof (induct p rule: iszlfm.induct)
  2417   case (5 c e) hence cp: "c>0" and be: "numbound0 e" and ei:"isint e (a#bs)" and d': "c dvd l" by simp+
  2418     from lp cp have clel: "c\<le>l" by (simp add: zdvd_imp_le [OF d' lp])
  2419     from cp have cnz: "c \<noteq> 0" by simp
  2420     have "c div c\<le> l div c"
  2421       by (simp add: zdiv_mono1[OF clel cp])
  2422     then have ldcp:"0 < l div c" 
  2423       by (simp add: div_self[OF cnz])
  2424     have "c * (l div c) = c* (l div c) + l mod c" using d' dvd_eq_mod_eq_0[of "c" "l"] by simp
  2425     hence cl:"c * (l div c) =l" using zmod_zdiv_equality[where a="l" and b="c", symmetric] 
  2426       by simp
  2427     hence "(real l * real x + real (l div c) * Inum (real x # bs) e < (0\<Colon>real)) =
  2428           (real (c * (l div c)) * real x + real (l div c) * Inum (real x # bs) e < 0)"
  2429       by simp
  2430     also have "\<dots> = (real (l div c) * (real c * real x + Inum (real x # bs) e) < (real (l div c)) * 0)" by (simp add: algebra_simps)
  2431     also have "\<dots> = (real c * real x + Inum (real x # bs) e < 0)"
  2432     using mult_less_0_iff [where a="real (l div c)" and b="real c * real x + Inum (real x # bs) e"] ldcp by simp
  2433   finally show ?case using numbound0_I[OF be,where b="real (l * x)" and b'="real x" and bs="bs"] be  isint_Mul[OF ei] by simp
  2434 next
  2435   case (6 c e) hence cp: "c>0" and be: "numbound0 e" and ei:"isint e (a#bs)" and d': "c dvd l" by simp+
  2436     from lp cp have clel: "c\<le>l" by (simp add: zdvd_imp_le [OF d' lp])
  2437     from cp have cnz: "c \<noteq> 0" by simp
  2438     have "c div c\<le> l div c"
  2439       by (simp add: zdiv_mono1[OF clel cp])
  2440     then have ldcp:"0 < l div c" 
  2441       by (simp add: div_self[OF cnz])
  2442     have "c * (l div c) = c* (l div c) + l mod c" using d' dvd_eq_mod_eq_0[of "c" "l"] by simp
  2443     hence cl:"c * (l div c) =l" using zmod_zdiv_equality[where a="l" and b="c", symmetric] 
  2444       by simp
  2445     hence "(real l * real x + real (l div c) * Inum (real x # bs) e \<le> (0\<Colon>real)) =
  2446           (real (c * (l div c)) * real x + real (l div c) * Inum (real x # bs) e \<le> 0)"
  2447       by simp
  2448     also have "\<dots> = (real (l div c) * (real c * real x + Inum (real x # bs) e) \<le> (real (l div c)) * 0)" by (simp add: algebra_simps)
  2449     also have "\<dots> = (real c * real x + Inum (real x # bs) e \<le> 0)"
  2450     using mult_le_0_iff [where a="real (l div c)" and b="real c * real x + Inum (real x # bs) e"] ldcp by simp
  2451   finally show ?case using numbound0_I[OF be,where b="real (l * x)" and b'="real x" and bs="bs"]  be  isint_Mul[OF ei] by simp
  2452 next
  2453   case (7 c e) hence cp: "c>0" and be: "numbound0 e" and ei:"isint e (a#bs)" and d': "c dvd l" by simp+
  2454     from lp cp have clel: "c\<le>l" by (simp add: zdvd_imp_le [OF d' lp])
  2455     from cp have cnz: "c \<noteq> 0" by simp
  2456     have "c div c\<le> l div c"
  2457       by (simp add: zdiv_mono1[OF clel cp])
  2458     then have ldcp:"0 < l div c" 
  2459       by (simp add: div_self[OF cnz])
  2460     have "c * (l div c) = c* (l div c) + l mod c" using d' dvd_eq_mod_eq_0[of "c" "l"] by simp
  2461     hence cl:"c * (l div c) =l" using zmod_zdiv_equality[where a="l" and b="c", symmetric] 
  2462       by simp
  2463     hence "(real l * real x + real (l div c) * Inum (real x # bs) e > (0\<Colon>real)) =
  2464           (real (c * (l div c)) * real x + real (l div c) * Inum (real x # bs) e > 0)"
  2465       by simp
  2466     also have "\<dots> = (real (l div c) * (real c * real x + Inum (real x # bs) e) > (real (l div c)) * 0)" by (simp add: algebra_simps)
  2467     also have "\<dots> = (real c * real x + Inum (real x # bs) e > 0)"
  2468     using zero_less_mult_iff [where a="real (l div c)" and b="real c * real x + Inum (real x # bs) e"] ldcp by simp
  2469   finally show ?case using numbound0_I[OF be,where b="real (l * x)" and b'="real x" and bs="bs"]  be  isint_Mul[OF ei] by simp
  2470 next
  2471   case (8 c e) hence cp: "c>0" and be: "numbound0 e"  and ei:"isint e (a#bs)" and d': "c dvd l" by simp+
  2472     from lp cp have clel: "c\<le>l" by (simp add: zdvd_imp_le [OF d' lp])
  2473     from cp have cnz: "c \<noteq> 0" by simp
  2474     have "c div c\<le> l div c"
  2475       by (simp add: zdiv_mono1[OF clel cp])
  2476     then have ldcp:"0 < l div c" 
  2477       by (simp add: div_self[OF cnz])
  2478     have "c * (l div c) = c* (l div c) + l mod c" using d' dvd_eq_mod_eq_0[of "c" "l"] by simp
  2479     hence cl:"c * (l div c) =l" using zmod_zdiv_equality[where a="l" and b="c", symmetric] 
  2480       by simp
  2481     hence "(real l * real x + real (l div c) * Inum (real x # bs) e \<ge> (0\<Colon>real)) =
  2482           (real (c * (l div c)) * real x + real (l div c) * Inum (real x # bs) e \<ge> 0)"
  2483       by simp
  2484     also have "\<dots> = (real (l div c) * (real c * real x + Inum (real x # bs) e) \<ge> (real (l div c)) * 0)" by (simp add: algebra_simps)
  2485     also have "\<dots> = (real c * real x + Inum (real x # bs) e \<ge> 0)"
  2486     using zero_le_mult_iff [where a="real (l div c)" and b="real c * real x + Inum (real x # bs) e"] ldcp by simp
  2487   finally show ?case using numbound0_I[OF be,where b="real (l * x)" and b'="real x" and bs="bs"]  be  isint_Mul[OF ei] by simp
  2488 next
  2489   case (3 c e) hence cp: "c>0" and be: "numbound0 e" and ei:"isint e (a#bs)" and d': "c dvd l" by simp+
  2490     from lp cp have clel: "c\<le>l" by (simp add: zdvd_imp_le [OF d' lp])
  2491     from cp have cnz: "c \<noteq> 0" by simp
  2492     have "c div c\<le> l div c"
  2493       by (simp add: zdiv_mono1[OF clel cp])
  2494     then have ldcp:"0 < l div c" 
  2495       by (simp add: div_self[OF cnz])
  2496     have "c * (l div c) = c* (l div c) + l mod c" using d' dvd_eq_mod_eq_0[of "c" "l"] by simp
  2497     hence cl:"c * (l div c) =l" using zmod_zdiv_equality[where a="l" and b="c", symmetric] 
  2498       by simp
  2499     hence "(real l * real x + real (l div c) * Inum (real x # bs) e = (0\<Colon>real)) =
  2500           (real (c * (l div c)) * real x + real (l div c) * Inum (real x # bs) e = 0)"
  2501       by simp
  2502     also have "\<dots> = (real (l div c) * (real c * real x + Inum (real x # bs) e) = (real (l div c)) * 0)" by (simp add: algebra_simps)
  2503     also have "\<dots> = (real c * real x + Inum (real x # bs) e = 0)"
  2504     using mult_eq_0_iff [where a="real (l div c)" and b="real c * real x + Inum (real x # bs) e"] ldcp by simp
  2505   finally show ?case using numbound0_I[OF be,where b="real (l * x)" and b'="real x" and bs="bs"]  be  isint_Mul[OF ei] by simp
  2506 next
  2507   case (4 c e) hence cp: "c>0" and be: "numbound0 e" and ei:"isint e (a#bs)" and d': "c dvd l" by simp+
  2508     from lp cp have clel: "c\<le>l" by (simp add: zdvd_imp_le [OF d' lp])
  2509     from cp have cnz: "c \<noteq> 0" by simp
  2510     have "c div c\<le> l div c"
  2511       by (simp add: zdiv_mono1[OF clel cp])
  2512     then have ldcp:"0 < l div c" 
  2513       by (simp add: div_self[OF cnz])
  2514     have "c * (l div c) = c* (l div c) + l mod c" using d' dvd_eq_mod_eq_0[of "c" "l"] by simp
  2515     hence cl:"c * (l div c) =l" using zmod_zdiv_equality[where a="l" and b="c", symmetric] 
  2516       by simp
  2517     hence "(real l * real x + real (l div c) * Inum (real x # bs) e \<noteq> (0\<Colon>real)) =
  2518           (real (c * (l div c)) * real x + real (l div c) * Inum (real x # bs) e \<noteq> 0)"
  2519       by simp
  2520     also have "\<dots> = (real (l div c) * (real c * real x + Inum (real x # bs) e) \<noteq> (real (l div c)) * 0)" by (simp add: algebra_simps)
  2521     also have "\<dots> = (real c * real x + Inum (real x # bs) e \<noteq> 0)"
  2522     using zero_le_mult_iff [where a="real (l div c)" and b="real c * real x + Inum (real x # bs) e"] ldcp by simp
  2523   finally show ?case using numbound0_I[OF be,where b="real (l * x)" and b'="real x" and bs="bs"]  be  isint_Mul[OF ei] by simp
  2524 next
  2525   case (9 j c e) hence cp: "c>0" and be: "numbound0 e" and ei:"isint e (a#bs)" and jp: "j > 0" and d': "c dvd l" by simp+
  2526     from lp cp have clel: "c\<le>l" by (simp add: zdvd_imp_le [OF d' lp])
  2527     from cp have cnz: "c \<noteq> 0" by simp
  2528     have "c div c\<le> l div c"
  2529       by (simp add: zdiv_mono1[OF clel cp])
  2530     then have ldcp:"0 < l div c" 
  2531       by (simp add: div_self[OF cnz])
  2532     have "c * (l div c) = c* (l div c) + l mod c" using d' dvd_eq_mod_eq_0[of "c" "l"] by simp
  2533     hence cl:"c * (l div c) =l" using zmod_zdiv_equality[where a="l" and b="c", symmetric] 
  2534       by simp
  2535     hence "(\<exists> (k::int). real l * real x + real (l div c) * Inum (real x # bs) e = (real (l div c) * real j) * real k) = (\<exists> (k::int). real (c * (l div c)) * real x + real (l div c) * Inum (real x # bs) e = (real (l div c) * real j) * real k)"  by simp
  2536     also have "\<dots> = (\<exists> (k::int). real (l div c) * (real c * real x + Inum (real x # bs) e - real j * real k) = real (l div c)*0)" by (simp add: algebra_simps)
  2537     also fix k have "\<dots> = (\<exists> (k::int). real c * real x + Inum (real x # bs) e - real j * real k = 0)"
  2538     using zero_le_mult_iff [where a="real (l div c)" and b="real c * real x + Inum (real x # bs) e - real j * real k"] ldcp by simp
  2539   also have "\<dots> = (\<exists> (k::int). real c * real x + Inum (real x # bs) e = real j * real k)" by simp
  2540   finally show ?case using numbound0_I[OF be,where b="real (l * x)" and b'="real x" and bs="bs"] rdvd_def  be  isint_Mul[OF ei] mult_strict_mono[OF ldcp jp ldcp ] by simp 
  2541 next
  2542   case (10 j c e) hence cp: "c>0" and be: "numbound0 e" and ei:"isint e (a#bs)" and jp: "j > 0" and d': "c dvd l" by simp+
  2543     from lp cp have clel: "c\<le>l" by (simp add: zdvd_imp_le [OF d' lp])
  2544     from cp have cnz: "c \<noteq> 0" by simp
  2545     have "c div c\<le> l div c"
  2546       by (simp add: zdiv_mono1[OF clel cp])
  2547     then have ldcp:"0 < l div c" 
  2548       by (simp add: div_self[OF cnz])
  2549     have "c * (l div c) = c* (l div c) + l mod c" using d' dvd_eq_mod_eq_0[of "c" "l"] by simp
  2550     hence cl:"c * (l div c) =l" using zmod_zdiv_equality[where a="l" and b="c", symmetric] 
  2551       by simp
  2552     hence "(\<exists> (k::int). real l * real x + real (l div c) * Inum (real x # bs) e = (real (l div c) * real j) * real k) = (\<exists> (k::int). real (c * (l div c)) * real x + real (l div c) * Inum (real x # bs) e = (real (l div c) * real j) * real k)"  by simp
  2553     also have "\<dots> = (\<exists> (k::int). real (l div c) * (real c * real x + Inum (real x # bs) e - real j * real k) = real (l div c)*0)" by (simp add: algebra_simps)
  2554     also fix k have "\<dots> = (\<exists> (k::int). real c * real x + Inum (real x # bs) e - real j * real k = 0)"
  2555     using zero_le_mult_iff [where a="real (l div c)" and b="real c * real x + Inum (real x # bs) e - real j * real k"] ldcp by simp
  2556   also have "\<dots> = (\<exists> (k::int). real c * real x + Inum (real x # bs) e = real j * real k)" by simp
  2557   finally show ?case using numbound0_I[OF be,where b="real (l * x)" and b'="real x" and bs="bs"] rdvd_def  be  isint_Mul[OF ei]  mult_strict_mono[OF ldcp jp ldcp ] by simp
  2558 qed (simp_all add: numbound0_I[where bs="bs" and b="real (l * x)" and b'="real x"] isint_Mul del: real_of_int_mult)
  2559 
  2560 lemma a\<beta>_ex: assumes linp: "iszlfm p (a#bs)" and d: "d\<beta> p l" and lp: "l>0"
  2561   shows "(\<exists> x. l dvd x \<and> Ifm (real x #bs) (a\<beta> p l)) = (\<exists> (x::int). Ifm (real x#bs) p)"
  2562   (is "(\<exists> x. l dvd x \<and> ?P x) = (\<exists> x. ?P' x)")
  2563 proof-
  2564   have "(\<exists> x. l dvd x \<and> ?P x) = (\<exists> (x::int). ?P (l*x))"
  2565     using unity_coeff_ex[where l="l" and P="?P", simplified] by simp
  2566   also have "\<dots> = (\<exists> (x::int). ?P' x)" using a\<beta>[OF linp d lp] by simp
  2567   finally show ?thesis  . 
  2568 qed
  2569 
  2570 lemma \<beta>:
  2571   assumes lp: "iszlfm p (a#bs)"
  2572   and u: "d\<beta> p 1"
  2573   and d: "d\<delta> p d"
  2574   and dp: "d > 0"
  2575   and nob: "\<not>(\<exists>(j::int) \<in> {1 .. d}. \<exists> b\<in> (Inum (a#bs)) ` set(\<beta> p). real x = b + real j)"
  2576   and p: "Ifm (real x#bs) p" (is "?P x")
  2577   shows "?P (x - d)"
  2578 using lp u d dp nob p
  2579 proof(induct p rule: iszlfm.induct)
  2580   case (5 c e) hence c1: "c=1" and  bn:"numbound0 e" using dvd1_eq1[where x="c"] by simp_all
  2581   with dp p c1 numbound0_I[OF bn,where b="real (x-d)" and b'="real x" and bs="bs"] 5
  2582   show ?case by (simp del: real_of_int_minus)
  2583 next
  2584   case (6 c e)  hence c1: "c=1" and  bn:"numbound0 e" using dvd1_eq1[where x="c"] by simp_all
  2585   with dp p c1 numbound0_I[OF bn,where b="real (x-d)" and b'="real x" and bs="bs"] 6
  2586   show ?case by (simp del: real_of_int_minus)
  2587 next
  2588   case (7 c e) hence p: "Ifm (real x #bs) (Gt (CN 0 c e))" and c1: "c=1"
  2589     and bn:"numbound0 e" and ie1:"isint e (a#bs)" using dvd1_eq1[where x="c"] by simp_all
  2590   let ?e = "Inum (real x # bs) e"
  2591   from ie1 have ie: "real (floor ?e) = ?e" using isint_iff[where n="e" and bs="a#bs"]
  2592       numbound0_I[OF bn,where b="a" and b'="real x" and bs="bs"]
  2593     by (simp add: isint_iff)
  2594     {assume "real (x-d) +?e > 0" hence ?case using c1 
  2595       numbound0_I[OF bn,where b="real (x-d)" and b'="real x" and bs="bs"]
  2596         by (simp del: real_of_int_minus)}
  2597     moreover
  2598     {assume H: "\<not> real (x-d) + ?e > 0" 
  2599       let ?v="Neg e"
  2600       have vb: "?v \<in> set (\<beta> (Gt (CN 0 c e)))" by simp
  2601       from 7(5)[simplified simp_thms Inum.simps \<beta>.simps set.simps bex_simps numbound0_I[OF bn,where b="a" and b'="real x" and bs="bs"]] 
  2602       have nob: "\<not> (\<exists> j\<in> {1 ..d}. real x =  - ?e + real j)" by auto 
  2603       from H p have "real x + ?e > 0 \<and> real x + ?e \<le> real d" by (simp add: c1)
  2604       hence "real (x + floor ?e) > real (0::int) \<and> real (x + floor ?e) \<le> real d"
  2605         using ie by simp
  2606       hence "x + floor ?e \<ge> 1 \<and> x + floor ?e \<le> d"  by simp
  2607       hence "\<exists> (j::int) \<in> {1 .. d}. j = x + floor ?e" by simp
  2608       hence "\<exists> (j::int) \<in> {1 .. d}. real x = real (- floor ?e + j)" 
  2609         by (simp only: real_of_int_inject) (simp add: algebra_simps)
  2610       hence "\<exists> (j::int) \<in> {1 .. d}. real x = - ?e + real j" 
  2611         by (simp add: ie[simplified isint_iff])
  2612       with nob have ?case by auto}
  2613     ultimately show ?case by blast
  2614 next
  2615   case (8 c e) hence p: "Ifm (real x #bs) (Ge (CN 0 c e))" and c1: "c=1" and bn:"numbound0 e" 
  2616     and ie1:"isint e (a #bs)" using dvd1_eq1[where x="c"] by simp+
  2617     let ?e = "Inum (real x # bs) e"
  2618     from ie1 have ie: "real (floor ?e) = ?e" using numbound0_I[OF bn,where b="real x" and b'="a" and bs="bs"] isint_iff[where n="e" and bs="(real x)#bs"]
  2619       by (simp add: isint_iff)
  2620     {assume "real (x-d) +?e \<ge> 0" hence ?case using  c1 
  2621       numbound0_I[OF bn,where b="real (x-d)" and b'="real x" and bs="bs"]
  2622         by (simp del: real_of_int_minus)}
  2623     moreover
  2624     {assume H: "\<not> real (x-d) + ?e \<ge> 0" 
  2625       let ?v="Sub (C -1) e"
  2626       have vb: "?v \<in> set (\<beta> (Ge (CN 0 c e)))" by simp
  2627       from 8(5)[simplified simp_thms Inum.simps \<beta>.simps set.simps bex_simps numbound0_I[OF bn,where b="a" and b'="real x" and bs="bs"]] 
  2628       have nob: "\<not> (\<exists> j\<in> {1 ..d}. real x =  - ?e - 1 + real j)" by auto 
  2629       from H p have "real x + ?e \<ge> 0 \<and> real x + ?e < real d" by (simp add: c1)
  2630       hence "real (x + floor ?e) \<ge> real (0::int) \<and> real (x + floor ?e) < real d"
  2631         using ie by simp
  2632       hence "x + floor ?e +1 \<ge> 1 \<and> x + floor ?e + 1 \<le> d"  by simp
  2633       hence "\<exists> (j::int) \<in> {1 .. d}. j = x + floor ?e + 1" by simp
  2634       hence "\<exists> (j::int) \<in> {1 .. d}. x= - floor ?e - 1 + j" by (simp add: algebra_simps)
  2635       hence "\<exists> (j::int) \<in> {1 .. d}. real x= real (- floor ?e - 1 + j)" 
  2636         by (simp only: real_of_int_inject)
  2637       hence "\<exists> (j::int) \<in> {1 .. d}. real x= - ?e - 1 + real j" 
  2638         by (simp add: ie[simplified isint_iff])
  2639       with nob have ?case by simp }
  2640     ultimately show ?case by blast
  2641 next
  2642   case (3 c e) hence p: "Ifm (real x #bs) (Eq (CN 0 c e))" (is "?p x") and c1: "c=1" 
  2643     and bn:"numbound0 e" and ie1: "isint e (a #bs)" using dvd1_eq1[where x="c"] by simp+
  2644     let ?e = "Inum (real x # bs) e"
  2645     let ?v="(Sub (C -1) e)"
  2646     have vb: "?v \<in> set (\<beta> (Eq (CN 0 c e)))" by simp
  2647     from p have "real x= - ?e" by (simp add: c1) with 3(5) show ?case using dp
  2648       by simp (erule ballE[where x="1"],
  2649         simp_all add:algebra_simps numbound0_I[OF bn,where b="real x"and b'="a"and bs="bs"])
  2650 next
  2651   case (4 c e)hence p: "Ifm (real x #bs) (NEq (CN 0 c e))" (is "?p x") and c1: "c=1" 
  2652     and bn:"numbound0 e" and ie1: "isint e (a #bs)" using dvd1_eq1[where x="c"] by simp+
  2653     let ?e = "Inum (real x # bs) e"
  2654     let ?v="Neg e"
  2655     have vb: "?v \<in> set (\<beta> (NEq (CN 0 c e)))" by simp
  2656     {assume "real x - real d + Inum ((real (x -d)) # bs) e \<noteq> 0" 
  2657       hence ?case by (simp add: c1)}
  2658     moreover
  2659     {assume H: "real x - real d + Inum ((real (x -d)) # bs) e = 0"
  2660       hence "real x = - Inum ((real (x -d)) # bs) e + real d" by simp
  2661       hence "real x = - Inum (a # bs) e + real d"
  2662         by (simp add: numbound0_I[OF bn,where b="real x - real d"and b'="a"and bs="bs"])
  2663        with 4(5) have ?case using dp by simp}
  2664   ultimately show ?case by blast
  2665 next 
  2666   case (9 j c e) hence p: "Ifm (real x #bs) (Dvd j (CN 0 c e))" (is "?p x") and c1: "c=1" 
  2667     and bn:"numbound0 e" using dvd1_eq1[where x="c"] by simp+
  2668   let ?e = "Inum (real x # bs) e"
  2669   from 9 have "isint e (a #bs)"  by simp 
  2670   hence ie: "real (floor ?e) = ?e" using isint_iff[where n="e" and bs="(real x)#bs"] numbound0_I[OF bn,where b="real x" and b'="a" and bs="bs"]
  2671     by (simp add: isint_iff)
  2672   from 9 have id: "j dvd d" by simp
  2673   from c1 ie[symmetric] have "?p x = (real j rdvd real (x+ floor ?e))" by simp
  2674   also have "\<dots> = (j dvd x + floor ?e)" 
  2675     using int_rdvd_real[where i="j" and x="real (x+ floor ?e)"] by simp
  2676   also have "\<dots> = (j dvd x - d + floor ?e)" 
  2677     using dvd_period[OF id, where x="x" and c="-1" and t="floor ?e"] by simp
  2678   also have "\<dots> = (real j rdvd real (x - d + floor ?e))" 
  2679     using int_rdvd_real[where i="j" and x="real (x-d + floor ?e)",symmetric, simplified]
  2680       ie by simp
  2681   also have "\<dots> = (real j rdvd real x - real d + ?e)" 
  2682     using ie by simp
  2683   finally show ?case 
  2684     using numbound0_I[OF bn,where b="real (x-d)" and b'="real x" and bs="bs"] c1 p by simp
  2685 next
  2686   case (10 j c e) hence p: "Ifm (real x #bs) (NDvd j (CN 0 c e))" (is "?p x") and c1: "c=1" and bn:"numbound0 e" using dvd1_eq1[where x="c"] by simp+
  2687   let ?e = "Inum (real x # bs) e"
  2688   from 10 have "isint e (a#bs)"  by simp 
  2689   hence ie: "real (floor ?e) = ?e" using numbound0_I[OF bn,where b="real x" and b'="a" and bs="bs"] isint_iff[where n="e" and bs="(real x)#bs"]
  2690     by (simp add: isint_iff)
  2691   from 10 have id: "j dvd d" by simp
  2692   from c1 ie[symmetric] have "?p x = (\<not> real j rdvd real (x+ floor ?e))" by simp
  2693   also have "\<dots> = (\<not> j dvd x + floor ?e)" 
  2694     using int_rdvd_real[where i="j" and x="real (x+ floor ?e)"] by simp
  2695   also have "\<dots> = (\<not> j dvd x - d + floor ?e)" 
  2696     using dvd_period[OF id, where x="x" and c="-1" and t="floor ?e"] by simp
  2697   also have "\<dots> = (\<not> real j rdvd real (x - d + floor ?e))" 
  2698     using int_rdvd_real[where i="j" and x="real (x-d + floor ?e)",symmetric, simplified]
  2699       ie by simp
  2700   also have "\<dots> = (\<not> real j rdvd real x - real d + ?e)" 
  2701     using ie by simp
  2702   finally show ?case
  2703     using numbound0_I[OF bn,where b="real (x-d)" and b'="real x" and bs="bs"] c1 p by simp
  2704 qed (auto simp add: numbound0_I[where bs="bs" and b="real (x - d)" and b'="real x"]
  2705   simp del: real_of_int_diff)
  2706 
  2707 lemma \<beta>':   
  2708   assumes lp: "iszlfm p (a #bs)"
  2709   and u: "d\<beta> p 1"
  2710   and d: "d\<delta> p d"
  2711   and dp: "d > 0"
  2712   shows "\<forall> x. \<not>(\<exists>(j::int) \<in> {1 .. d}. \<exists> b\<in> set(\<beta> p). Ifm ((Inum (a#bs) b + real j) #bs) p) \<longrightarrow> Ifm (real x#bs) p \<longrightarrow> Ifm (real (x - d)#bs) p" (is "\<forall> x. ?b \<longrightarrow> ?P x \<longrightarrow> ?P (x - d)")
  2713 proof(clarify)
  2714   fix x 
  2715   assume nb:"?b" and px: "?P x" 
  2716   hence nb2: "\<not>(\<exists>(j::int) \<in> {1 .. d}. \<exists> b\<in> (Inum (a#bs)) ` set(\<beta> p). real x = b + real j)"
  2717     by auto
  2718   from  \<beta>[OF lp u d dp nb2 px] show "?P (x -d )" .
  2719 qed
  2720 
  2721 lemma \<beta>_int: assumes lp: "iszlfm p bs"
  2722   shows "\<forall> b\<in> set (\<beta> p). isint b bs"
  2723 using lp by (induct p rule: iszlfm.induct) (auto simp add: isint_neg isint_sub)
  2724 
  2725 lemma cpmi_eq: "0 < D \<Longrightarrow> (EX z::int. ALL x. x < z --> (P x = P1 x))
  2726 ==> ALL x.~(EX (j::int) : {1..D}. EX (b::int) : B. P(b+j)) --> P (x) --> P (x - D) 
  2727 ==> (ALL (x::int). ALL (k::int). ((P1 x)= (P1 (x-k*D))))
  2728 ==> (EX (x::int). P(x)) = ((EX (j::int) : {1..D} . (P1(j))) | (EX (j::int) : {1..D}. EX (b::int) : B. P (b+j)))"
  2729 apply(rule iffI)
  2730 prefer 2
  2731 apply(drule minusinfinity)
  2732 apply assumption+
  2733 apply(fastforce)
  2734 apply clarsimp
  2735 apply(subgoal_tac "!!k. 0<=k \<Longrightarrow> !x. P x \<longrightarrow> P (x - k*D)")
  2736 apply(frule_tac x = x and z=z in decr_lemma)
  2737 apply(subgoal_tac "P1(x - (\<bar>x - z\<bar> + 1) * D)")
  2738 prefer 2
  2739 apply(subgoal_tac "0 <= (\<bar>x - z\<bar> + 1)")
  2740 prefer 2 apply arith
  2741  apply fastforce
  2742 apply(drule (1)  periodic_finite_ex)
  2743 apply blast
  2744 apply(blast dest:decr_mult_lemma)
  2745 done
  2746 
  2747 
  2748 theorem cp_thm:
  2749   assumes lp: "iszlfm p (a #bs)"
  2750   and u: "d\<beta> p 1"
  2751   and d: "d\<delta> p d"
  2752   and dp: "d > 0"
  2753   shows "(\<exists> (x::int). Ifm (real x #bs) p) = (\<exists> j\<in> {1.. d}. Ifm (real j #bs) (minusinf p) \<or> (\<exists> b \<in> set (\<beta> p). Ifm ((Inum (a#bs) b + real j) #bs) p))"
  2754   (is "(\<exists> (x::int). ?P (real x)) = (\<exists> j\<in> ?D. ?M j \<or> (\<exists> b\<in> ?B. ?P (?I b + real j)))")
  2755 proof-
  2756   from minusinf_inf[OF lp] 
  2757   have th: "\<exists>(z::int). \<forall>x<z. ?P (real x) = ?M x" by blast
  2758   let ?B' = "{floor (?I b) | b. b\<in> ?B}"
  2759   from \<beta>_int[OF lp] isint_iff[where bs="a # bs"] have B: "\<forall> b\<in> ?B. real (floor (?I b)) = ?I b" by simp
  2760   from B[rule_format] 
  2761   have "(\<exists>j\<in>?D. \<exists>b\<in> ?B. ?P (?I b + real j)) = (\<exists>j\<in>?D. \<exists>b\<in> ?B. ?P (real (floor (?I b)) + real j))" 
  2762     by simp
  2763   also have "\<dots> = (\<exists>j\<in>?D. \<exists>b\<in> ?B. ?P (real (floor (?I b) + j)))" by simp
  2764   also have"\<dots> = (\<exists> j \<in> ?D. \<exists> b \<in> ?B'. ?P (real (b + j)))"  by blast
  2765   finally have BB': 
  2766     "(\<exists>j\<in>?D. \<exists>b\<in> ?B. ?P (?I b + real j)) = (\<exists> j \<in> ?D. \<exists> b \<in> ?B'. ?P (real (b + j)))" 
  2767     by blast 
  2768   hence th2: "\<forall> x. \<not> (\<exists> j \<in> ?D. \<exists> b \<in> ?B'. ?P (real (b + j))) \<longrightarrow> ?P (real x) \<longrightarrow> ?P (real (x - d))" using \<beta>'[OF lp u d dp] by blast
  2769   from minusinf_repeats[OF d lp]
  2770   have th3: "\<forall> x k. ?M x = ?M (x-k*d)" by simp
  2771   from cpmi_eq[OF dp th th2 th3] BB' show ?thesis by blast
  2772 qed
  2773 
  2774     (* Reddy and Loveland *)
  2775 
  2776 
  2777 consts 
  2778   \<rho> :: "fm \<Rightarrow> (num \<times> int) list" (* Compute the Reddy and Loveland Bset*)
  2779   \<sigma>\<rho>:: "fm \<Rightarrow> num \<times> int \<Rightarrow> fm" (* Performs the modified substitution of Reddy and Loveland*)
  2780   \<alpha>\<rho> :: "fm \<Rightarrow> (num\<times>int) list"
  2781   a\<rho> :: "fm \<Rightarrow> int \<Rightarrow> fm"
  2782 recdef \<rho> "measure size"
  2783   "\<rho> (And p q) = (\<rho> p @ \<rho> q)" 
  2784   "\<rho> (Or p q) = (\<rho> p @ \<rho> q)" 
  2785   "\<rho> (Eq  (CN 0 c e)) = [(Sub (C -1) e,c)]"
  2786   "\<rho> (NEq (CN 0 c e)) = [(Neg e,c)]"
  2787   "\<rho> (Lt  (CN 0 c e)) = []"
  2788   "\<rho> (Le  (CN 0 c e)) = []"
  2789   "\<rho> (Gt  (CN 0 c e)) = [(Neg e, c)]"
  2790   "\<rho> (Ge  (CN 0 c e)) = [(Sub (C (-1)) e, c)]"
  2791   "\<rho> p = []"
  2792 
  2793 recdef \<sigma>\<rho> "measure size"
  2794   "\<sigma>\<rho> (And p q) = (\<lambda> (t,k). And (\<sigma>\<rho> p (t,k)) (\<sigma>\<rho> q (t,k)))" 
  2795   "\<sigma>\<rho> (Or p q) = (\<lambda> (t,k). Or (\<sigma>\<rho> p (t,k)) (\<sigma>\<rho> q (t,k)))" 
  2796   "\<sigma>\<rho> (Eq  (CN 0 c e)) = (\<lambda> (t,k). if k dvd c then (Eq (Add (Mul (c div k) t) e)) 
  2797                                             else (Eq (Add (Mul c t) (Mul k e))))"
  2798   "\<sigma>\<rho> (NEq (CN 0 c e)) = (\<lambda> (t,k). if k dvd c then (NEq (Add (Mul (c div k) t) e)) 
  2799                                             else (NEq (Add (Mul c t) (Mul k e))))"
  2800   "\<sigma>\<rho> (Lt  (CN 0 c e)) = (\<lambda> (t,k). if k dvd c then (Lt (Add (Mul (c div k) t) e)) 
  2801                                             else (Lt (Add (Mul c t) (Mul k e))))"
  2802   "\<sigma>\<rho> (Le  (CN 0 c e)) = (\<lambda> (t,k). if k dvd c then (Le (Add (Mul (c div k) t) e)) 
  2803                                             else (Le (Add (Mul c t) (Mul k e))))"
  2804   "\<sigma>\<rho> (Gt  (CN 0 c e)) = (\<lambda> (t,k). if k dvd c then (Gt (Add (Mul (c div k) t) e)) 
  2805                                             else (Gt (Add (Mul c t) (Mul k e))))"
  2806   "\<sigma>\<rho> (Ge  (CN 0 c e)) = (\<lambda> (t,k). if k dvd c then (Ge (Add (Mul (c div k) t) e)) 
  2807                                             else (Ge (Add (Mul c t) (Mul k e))))"
  2808   "\<sigma>\<rho> (Dvd i (CN 0 c e)) =(\<lambda> (t,k). if k dvd c then (Dvd i (Add (Mul (c div k) t) e)) 
  2809                                             else (Dvd (i*k) (Add (Mul c t) (Mul k e))))"
  2810   "\<sigma>\<rho> (NDvd i (CN 0 c e))=(\<lambda> (t,k). if k dvd c then (NDvd i (Add (Mul (c div k) t) e)) 
  2811                                             else (NDvd (i*k) (Add (Mul c t) (Mul k e))))"
  2812   "\<sigma>\<rho> p = (\<lambda> (t,k). p)"
  2813 
  2814 recdef \<alpha>\<rho> "measure size"
  2815   "\<alpha>\<rho> (And p q) = (\<alpha>\<rho> p @ \<alpha>\<rho> q)" 
  2816   "\<alpha>\<rho> (Or p q) = (\<alpha>\<rho> p @ \<alpha>\<rho> q)" 
  2817   "\<alpha>\<rho> (Eq  (CN 0 c e)) = [(Add (C -1) e,c)]"
  2818   "\<alpha>\<rho> (NEq (CN 0 c e)) = [(e,c)]"
  2819   "\<alpha>\<rho> (Lt  (CN 0 c e)) = [(e,c)]"
  2820   "\<alpha>\<rho> (Le  (CN 0 c e)) = [(Add (C -1) e,c)]"
  2821   "\<alpha>\<rho> p = []"
  2822 
  2823     (* Simulates normal substituion by modifying the formula see correctness theorem *)
  2824 
  2825 definition \<sigma> :: "fm \<Rightarrow> int \<Rightarrow> num \<Rightarrow> fm" where
  2826   "\<sigma> p k t \<equiv> And (Dvd k t) (\<sigma>\<rho> p (t,k))"
  2827 
  2828 lemma \<sigma>\<rho>:
  2829   assumes linp: "iszlfm p (real (x::int)#bs)"
  2830   and kpos: "real k > 0"
  2831   and tnb: "numbound0 t"
  2832   and tint: "isint t (real x#bs)"
  2833   and kdt: "k dvd floor (Inum (b'#bs) t)"
  2834   shows "Ifm (real x#bs) (\<sigma>\<rho> p (t,k)) = 
  2835   (Ifm ((real ((floor (Inum (b'#bs) t)) div k))#bs) p)" 
  2836   (is "?I (real x) (?s p) = (?I (real ((floor (?N b' t)) div k)) p)" is "_ = (?I ?tk p)")
  2837 using linp kpos tnb
  2838 proof(induct p rule: \<sigma>\<rho>.induct)
  2839   case (3 c e) 
  2840   from 3 have cp: "c > 0" and nb: "numbound0 e" by auto
  2841   { assume kdc: "k dvd c" 
  2842     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2843     from kdc have ?case using real_of_int_div[OF kdc] real_of_int_div[OF kdt]
  2844       numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2845       numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"] by (simp add: ti) } 
  2846   moreover 
  2847   { assume *: "\<not> k dvd c"
  2848     from kpos have knz': "real k \<noteq> 0" by simp
  2849     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t"
  2850       using isint_def by simp
  2851     from assms * have "?I (real x) (?s (Eq (CN 0 c e))) = ((real c * (?N (real x) t / real k) + ?N (real x) e)* real k = 0)"
  2852       using real_of_int_div[OF kdt]
  2853         numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2854         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2855       by (simp add: ti algebra_simps)
  2856       also have "\<dots> = (?I ?tk (Eq (CN 0 c e)))"
  2857         using nonzero_eq_divide_eq[OF knz',
  2858             where a="real c * (?N (real x) t / real k) + ?N (real x) e" and b="0", symmetric]
  2859           real_of_int_div[OF kdt] numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2860           numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2861         by (simp add: ti)
  2862       finally have ?case . }
  2863     ultimately show ?case by blast 
  2864 next
  2865   case (4 c e)  
  2866   then have cp: "c > 0" and nb: "numbound0 e" by auto
  2867   { assume kdc: "k dvd c" 
  2868     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2869     from kdc have  ?case using real_of_int_div[OF kdc] real_of_int_div[OF kdt]
  2870       numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2871       numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"] by (simp add: ti) } 
  2872   moreover 
  2873   { assume *: "\<not> k dvd c"
  2874     from kpos have knz': "real k \<noteq> 0" by simp
  2875     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2876     from assms * have "?I (real x) (?s (NEq (CN 0 c e))) = ((real c * (?N (real x) t / real k) + ?N (real x) e)* real k \<noteq> 0)"
  2877       using real_of_int_div[OF kdt]
  2878         numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2879         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2880       by (simp add: ti algebra_simps)
  2881     also have "\<dots> = (?I ?tk (NEq (CN 0 c e)))"
  2882       using nonzero_eq_divide_eq[OF knz',
  2883           where a="real c * (?N (real x) t / real k) + ?N (real x) e" and b="0", symmetric]
  2884         real_of_int_div[OF kdt] numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2885         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2886       by (simp add: ti)
  2887     finally have ?case . }
  2888   ultimately show ?case by blast 
  2889 next
  2890   case (5 c e) 
  2891   then have cp: "c > 0" and nb: "numbound0 e" by auto
  2892   { assume kdc: "k dvd c" 
  2893     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2894     from kdc have  ?case using real_of_int_div[OF kdc] real_of_int_div[OF kdt]
  2895       numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2896       numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"] by (simp add: ti) } 
  2897   moreover 
  2898   { assume *: "\<not> k dvd c"
  2899     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2900     from assms * have "?I (real x) (?s (Lt (CN 0 c e))) = ((real c * (?N (real x) t / real k) + ?N (real x) e)* real k < 0)"
  2901       using real_of_int_div[OF kdt]
  2902         numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2903         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2904       by (simp add: ti algebra_simps)
  2905     also have "\<dots> = (?I ?tk (Lt (CN 0 c e)))"
  2906       using pos_less_divide_eq[OF kpos,
  2907           where a="real c * (?N (real x) t / real k) + ?N (real x) e" and b="0", symmetric]
  2908         real_of_int_div[OF kdt] numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2909         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2910       by (simp add: ti)
  2911     finally have ?case . }
  2912   ultimately show ?case by blast 
  2913 next
  2914   case (6 c e)
  2915   then have cp: "c > 0" and nb: "numbound0 e" by auto
  2916   { assume kdc: "k dvd c" 
  2917     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2918     from kdc have  ?case using real_of_int_div[OF kdc] real_of_int_div[OF kdt]
  2919       numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2920       numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"] by (simp add: ti) } 
  2921   moreover 
  2922   { assume *: "\<not> k dvd c"
  2923     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2924     from assms * have "?I (real x) (?s (Le (CN 0 c e))) = ((real c * (?N (real x) t / real k) + ?N (real x) e)* real k \<le> 0)"
  2925       using real_of_int_div[OF kdt]
  2926         numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2927         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2928       by (simp add: ti algebra_simps)
  2929     also have "\<dots> = (?I ?tk (Le (CN 0 c e)))"
  2930       using pos_le_divide_eq[OF kpos,
  2931           where a="real c * (?N (real x) t / real k) + ?N (real x) e" and b="0", symmetric]
  2932         real_of_int_div[OF kdt] numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2933         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2934       by (simp add: ti)
  2935     finally have ?case . }
  2936   ultimately show ?case by blast 
  2937 next
  2938   case (7 c e) 
  2939   then have cp: "c > 0" and nb: "numbound0 e" by auto
  2940   { assume kdc: "k dvd c" 
  2941     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2942     from kdc have  ?case using real_of_int_div[OF kdc] real_of_int_div[OF kdt]
  2943       numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2944       numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"] by (simp add: ti) } 
  2945   moreover 
  2946   { assume *: "\<not> k dvd c"
  2947     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2948     from assms * have "?I (real x) (?s (Gt (CN 0 c e))) = ((real c * (?N (real x) t / real k) + ?N (real x) e)* real k > 0)"
  2949       using real_of_int_div[OF kdt]
  2950         numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2951         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2952       by (simp add: ti algebra_simps)
  2953     also have "\<dots> = (?I ?tk (Gt (CN 0 c e)))"
  2954       using pos_divide_less_eq[OF kpos,
  2955           where a="real c * (?N (real x) t / real k) + ?N (real x) e" and b="0", symmetric]
  2956         real_of_int_div[OF kdt] numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2957         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2958       by (simp add: ti)
  2959     finally have ?case . }
  2960   ultimately show ?case by blast 
  2961 next
  2962   case (8 c e)  
  2963   then have cp: "c > 0" and nb: "numbound0 e" by auto
  2964   { assume kdc: "k dvd c" 
  2965     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2966     from kdc have  ?case using real_of_int_div[OF kdc] real_of_int_div[OF kdt]
  2967       numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2968       numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"] by (simp add: ti) } 
  2969   moreover 
  2970   { assume *: "\<not> k dvd c"
  2971     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2972     from assms * have "?I (real x) (?s (Ge (CN 0 c e))) = ((real c * (?N (real x) t / real k) + ?N (real x) e)* real k \<ge> 0)"
  2973       using real_of_int_div[OF kdt]
  2974         numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2975         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2976       by (simp add: ti algebra_simps)
  2977     also have "\<dots> = (?I ?tk (Ge (CN 0 c e)))"
  2978       using pos_divide_le_eq[OF kpos,
  2979           where a="real c * (?N (real x) t / real k) + ?N (real x) e" and b="0", symmetric]
  2980         real_of_int_div[OF kdt] numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2981         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  2982       by (simp add: ti)
  2983     finally have ?case . }
  2984   ultimately show ?case by blast 
  2985 next
  2986   case (9 i c e)
  2987   then have cp: "c > 0" and nb: "numbound0 e" by auto
  2988   { assume kdc: "k dvd c" 
  2989     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2990     from kdc have ?case using real_of_int_div[OF kdc] real_of_int_div[OF kdt]
  2991       numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  2992       numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"] by (simp add: ti) } 
  2993   moreover 
  2994   { assume *: "\<not> k dvd c"
  2995     from kpos have knz: "k\<noteq>0" by simp hence knz': "real k \<noteq> 0" by simp
  2996     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  2997     from assms * have "?I (real x) (?s (Dvd i (CN 0 c e))) = (real i * real k rdvd (real c * (?N (real x) t / real k) + ?N (real x) e)* real k)"
  2998       using real_of_int_div[OF kdt]
  2999         numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  3000         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  3001       by (simp add: ti algebra_simps)
  3002     also have "\<dots> = (?I ?tk (Dvd i (CN 0 c e)))"
  3003       using rdvd_mult[OF knz, where n="i"]
  3004         real_of_int_div[OF kdt] numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  3005         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  3006       by (simp add: ti)
  3007     finally have ?case . }
  3008   ultimately show ?case by blast 
  3009 next
  3010   case (10 i c e)
  3011   then have cp: "c > 0" and nb: "numbound0 e" by auto
  3012   { assume kdc: "k dvd c" 
  3013     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  3014     from kdc have  ?case using real_of_int_div[OF kdc] real_of_int_div[OF kdt]
  3015       numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  3016       numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"] by (simp add: ti) } 
  3017   moreover 
  3018   { assume *: "\<not> k dvd c"
  3019     from kpos have knz: "k\<noteq>0" by simp hence knz': "real k \<noteq> 0" by simp
  3020     from tint have ti: "real (floor (?N (real x) t)) = ?N (real x) t" using isint_def by simp
  3021     from assms * have "?I (real x) (?s (NDvd i (CN 0 c e))) = (\<not> (real i * real k rdvd (real c * (?N (real x) t / real k) + ?N (real x) e)* real k))"
  3022       using real_of_int_div[OF kdt]
  3023         numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  3024         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  3025       by (simp add: ti algebra_simps)
  3026     also have "\<dots> = (?I ?tk (NDvd i (CN 0 c e)))"
  3027       using rdvd_mult[OF knz, where n="i"] real_of_int_div[OF kdt]
  3028         numbound0_I[OF tnb, where bs="bs" and b="b'" and b'="real x"]
  3029         numbound0_I[OF nb, where bs="bs" and b="?tk" and b'="real x"]
  3030       by (simp add: ti)
  3031     finally have ?case . }
  3032   ultimately show ?case by blast 
  3033 qed (simp_all add: bound0_I[where bs="bs" and b="real ((floor (?N b' t)) div k)" and b'="real x"]
  3034   numbound0_I[where bs="bs" and b="real ((floor (?N b' t)) div k)" and b'="real x"])
  3035 
  3036 
  3037 lemma \<sigma>\<rho>_nb: assumes lp:"iszlfm p (a#bs)" and nb: "numbound0 t"
  3038   shows "bound0 (\<sigma>\<rho> p (t,k))"
  3039   using lp
  3040   by (induct p rule: iszlfm.induct, auto simp add: nb)
  3041 
  3042 lemma \<rho>_l:
  3043   assumes lp: "iszlfm p (real (i::int)#bs)"
  3044   shows "\<forall> (b,k) \<in> set (\<rho> p). k >0 \<and> numbound0 b \<and> isint b (real i#bs)"
  3045 using lp by (induct p rule: \<rho>.induct, auto simp add: isint_sub isint_neg)
  3046 
  3047 lemma \<alpha>\<rho>_l:
  3048   assumes lp: "iszlfm p (real (i::int)#bs)"
  3049   shows "\<forall> (b,k) \<in> set (\<alpha>\<rho> p). k >0 \<and> numbound0 b \<and> isint b (real i#bs)"
  3050 using lp isint_add [OF isint_c[where j="- 1"],where bs="real i#bs"]
  3051  by (induct p rule: \<alpha>\<rho>.induct, auto)
  3052 
  3053 lemma \<rho>: assumes lp: "iszlfm p (real (i::int) #bs)"
  3054   and pi: "Ifm (real i#bs) p"
  3055   and d: "d\<delta> p d"
  3056   and dp: "d > 0"
  3057   and nob: "\<forall>(e,c) \<in> set (\<rho> p). \<forall> j\<in> {1 .. c*d}. real (c*i) \<noteq> Inum (real i#bs) e + real j"
  3058   (is "\<forall>(e,c) \<in> set (\<rho> p). \<forall> j\<in> {1 .. c*d}. _ \<noteq> ?N i e + _")
  3059   shows "Ifm (real(i - d)#bs) p"
  3060   using lp pi d nob
  3061 proof(induct p rule: iszlfm.induct)
  3062   case (3 c e) hence cp: "c >0" and nb: "numbound0 e" and ei: "isint e (real i#bs)"
  3063     and pi: "real (c*i) = - 1 -  ?N i e + real (1::int)" and nob: "\<forall> j\<in> {1 .. c*d}. real (c*i) \<noteq> -1 - ?N i e + real j"
  3064     by simp+
  3065   from mult_strict_left_mono[OF dp cp]  have one:"1 \<in> {1 .. c*d}" by auto
  3066   from nob[rule_format, where j="1", OF one] pi show ?case by simp
  3067 next
  3068   case (4 c e)  
  3069   hence cp: "c >0" and nb: "numbound0 e" and ei: "isint e (real i#bs)"
  3070     and nob: "\<forall> j\<in> {1 .. c*d}. real (c*i) \<noteq> - ?N i e + real j"
  3071     by simp+
  3072   {assume "real (c*i) \<noteq> - ?N i e + real (c*d)"
  3073     with numbound0_I[OF nb, where bs="bs" and b="real i - real d" and b'="real i"]
  3074     have ?case by (simp add: algebra_simps)}
  3075   moreover
  3076   {assume pi: "real (c*i) = - ?N i e + real (c*d)"
  3077     from mult_strict_left_mono[OF dp cp] have d: "(c*d) \<in> {1 .. c*d}" by simp
  3078     from nob[rule_format, where j="c*d", OF d] pi have ?case by simp }
  3079   ultimately show ?case by blast
  3080 next
  3081   case (5 c e) hence cp: "c > 0" by simp
  3082   from 5 mult_strict_left_mono[OF dp cp, simplified real_of_int_less_iff[symmetric] 
  3083     real_of_int_mult]
  3084   show ?case using 5 dp 
  3085     by (simp add: add: numbound0_I[where bs="bs" and b="real i - real d" and b'="real i"] 
  3086       algebra_simps)
  3087 next
  3088   case (6 c e) hence cp: "c > 0" by simp
  3089   from 6 mult_strict_left_mono[OF dp cp, simplified real_of_int_less_iff[symmetric] 
  3090     real_of_int_mult]
  3091   show ?case using 6 dp 
  3092     by (simp add: add: numbound0_I[where bs="bs" and b="real i - real d" and b'="real i"] 
  3093       algebra_simps)
  3094 next
  3095   case (7 c e) hence cp: "c >0" and nb: "numbound0 e" and ei: "isint e (real i#bs)"
  3096     and nob: "\<forall> j\<in> {1 .. c*d}. real (c*i) \<noteq> - ?N i e + real j"
  3097     and pi: "real (c*i) + ?N i e > 0" and cp': "real c >0"
  3098     by simp+
  3099   let ?fe = "floor (?N i e)"
  3100   from pi cp have th:"(real i +?N i e / real c)*real c > 0" by (simp add: algebra_simps)
  3101   from pi ei[simplified isint_iff] have "real (c*i + ?fe) > real (0::int)" by simp
  3102   hence pi': "c*i + ?fe > 0" by (simp only: real_of_int_less_iff[symmetric])
  3103   have "real (c*i) + ?N i e > real (c*d) \<or> real (c*i) + ?N i e \<le> real (c*d)" by auto
  3104   moreover
  3105   {assume "real (c*i) + ?N i e > real (c*d)" hence ?case
  3106       by (simp add: algebra_simps 
  3107         numbound0_I[OF nb,where bs="bs" and b="real i - real d" and b'="real i"])} 
  3108   moreover 
  3109   {assume H:"real (c*i) + ?N i e \<le> real (c*d)"
  3110     with ei[simplified isint_iff] have "real (c*i + ?fe) \<le> real (c*d)" by simp
  3111     hence pid: "c*i + ?fe \<le> c*d" by (simp only: real_of_int_le_iff)
  3112     with pi' have "\<exists> j1\<in> {1 .. c*d}. c*i + ?fe = j1" by auto
  3113     hence "\<exists> j1\<in> {1 .. c*d}. real (c*i) = - ?N i e + real j1" 
  3114       by (simp only: diff_minus[symmetric] real_of_int_mult real_of_int_add real_of_int_inject[symmetric] ei[simplified isint_iff] algebra_simps)
  3115     with nob  have ?case by blast }
  3116   ultimately show ?case by blast
  3117 next
  3118   case (8 c e)  hence cp: "c >0" and nb: "numbound0 e" and ei: "isint e (real i#bs)"
  3119     and nob: "\<forall> j\<in> {1 .. c*d}. real (c*i) \<noteq> - 1 - ?N i e + real j"
  3120     and pi: "real (c*i) + ?N i e \<ge> 0" and cp': "real c >0"
  3121     by simp+
  3122   let ?fe = "floor (?N i e)"
  3123   from pi cp have th:"(real i +?N i e / real c)*real c \<ge> 0" by (simp add: algebra_simps)
  3124   from pi ei[simplified isint_iff] have "real (c*i + ?fe) \<ge> real (0::int)" by simp
  3125   hence pi': "c*i + 1 + ?fe \<ge> 1" by (simp only: real_of_int_le_iff[symmetric])
  3126   have "real (c*i) + ?N i e \<ge> real (c*d) \<or> real (c*i) + ?N i e < real (c*d)" by auto
  3127   moreover
  3128   {assume "real (c*i) + ?N i e \<ge> real (c*d)" hence ?case
  3129       by (simp add: algebra_simps 
  3130         numbound0_I[OF nb,where bs="bs" and b="real i - real d" and b'="real i"])} 
  3131   moreover 
  3132   {assume H:"real (c*i) + ?N i e < real (c*d)"
  3133     with ei[simplified isint_iff] have "real (c*i + ?fe) < real (c*d)" by simp
  3134     hence pid: "c*i + 1 + ?fe \<le> c*d" by (simp only: real_of_int_le_iff)
  3135     with pi' have "\<exists> j1\<in> {1 .. c*d}. c*i + 1+ ?fe = j1" by auto
  3136     hence "\<exists> j1\<in> {1 .. c*d}. real (c*i) + 1= - ?N i e + real j1"
  3137       by (simp only: diff_minus[symmetric] real_of_int_mult real_of_int_add real_of_int_inject[symmetric] ei[simplified isint_iff] algebra_simps real_of_one) 
  3138     hence "\<exists> j1\<in> {1 .. c*d}. real (c*i) = (- ?N i e + real j1) - 1"
  3139       by (simp only: algebra_simps diff_minus[symmetric])
  3140         hence "\<exists> j1\<in> {1 .. c*d}. real (c*i) = - 1 - ?N i e + real j1"
  3141           by (simp only: add_ac diff_minus)
  3142     with nob  have ?case by blast }
  3143   ultimately show ?case by blast
  3144 next
  3145   case (9 j c e)  hence p: "real j rdvd real (c*i) + ?N i e" (is "?p x") and cp: "c > 0" and bn:"numbound0 e"  by simp+
  3146   let ?e = "Inum (real i # bs) e"
  3147   from 9 have "isint e (real i #bs)"  by simp 
  3148   hence ie: "real (floor ?e) = ?e" using isint_iff[where n="e" and bs="(real i)#bs"] numbound0_I[OF bn,where b="real i" and b'="real i" and bs="bs"]
  3149     by (simp add: isint_iff)
  3150   from 9 have id: "j dvd d" by simp
  3151   from ie[symmetric] have "?p i = (real j rdvd real (c*i+ floor ?e))" by simp
  3152   also have "\<dots> = (j dvd c*i + floor ?e)" 
  3153     using int_rdvd_iff [where i="j" and t="c*i+ floor ?e"] by simp
  3154   also have "\<dots> = (j dvd c*i - c*d + floor ?e)" 
  3155     using dvd_period[OF id, where x="c*i" and c="-c" and t="floor ?e"] by simp
  3156   also have "\<dots> = (real j rdvd real (c*i - c*d + floor ?e))" 
  3157     using int_rdvd_iff[where i="j" and t="(c*i - c*d + floor ?e)",symmetric, simplified]
  3158       ie by simp
  3159   also have "\<dots> = (real j rdvd real (c*(i - d)) + ?e)" 
  3160     using ie by (simp add:algebra_simps)
  3161   finally show ?case 
  3162     using numbound0_I[OF bn,where b="real i - real d" and b'="real i" and bs="bs"] p 
  3163     by (simp add: algebra_simps)
  3164 next
  3165   case (10 j c e)
  3166   hence p: "\<not> (real j rdvd real (c*i) + ?N i e)" (is "?p x") and cp: "c > 0" and bn:"numbound0 e"
  3167     by simp+
  3168   let ?e = "Inum (real i # bs) e"
  3169   from 10 have "isint e (real i #bs)"  by simp 
  3170   hence ie: "real (floor ?e) = ?e"
  3171     using isint_iff[where n="e" and bs="(real i)#bs"] numbound0_I[OF bn,where b="real i" and b'="real i" and bs="bs"]
  3172     by (simp add: isint_iff)
  3173   from 10 have id: "j dvd d" by simp
  3174   from ie[symmetric] have "?p i = (\<not> (real j rdvd real (c*i+ floor ?e)))" by simp
  3175   also have "\<dots> = Not (j dvd c*i + floor ?e)" 
  3176     using int_rdvd_iff [where i="j" and t="c*i+ floor ?e"] by simp
  3177   also have "\<dots> = Not (j dvd c*i - c*d + floor ?e)" 
  3178     using dvd_period[OF id, where x="c*i" and c="-c" and t="floor ?e"] by simp
  3179   also have "\<dots> = Not (real j rdvd real (c*i - c*d + floor ?e))" 
  3180     using int_rdvd_iff[where i="j" and t="(c*i - c*d + floor ?e)",symmetric, simplified]
  3181       ie by simp
  3182   also have "\<dots> = Not (real j rdvd real (c*(i - d)) + ?e)" 
  3183     using ie by (simp add:algebra_simps)
  3184   finally show ?case 
  3185     using numbound0_I[OF bn,where b="real i - real d" and b'="real i" and bs="bs"] p 
  3186     by (simp add: algebra_simps)
  3187 qed (auto simp add: numbound0_I[where bs="bs" and b="real i - real d" and b'="real i"])
  3188 
  3189 lemma \<sigma>_nb: assumes lp: "iszlfm p (a#bs)" and nb: "numbound0 t"
  3190   shows "bound0 (\<sigma> p k t)"
  3191   using \<sigma>\<rho>_nb[OF lp nb] nb by (simp add: \<sigma>_def)
  3192   
  3193 lemma \<rho>':   assumes lp: "iszlfm p (a #bs)"
  3194   and d: "d\<delta> p d"
  3195   and dp: "d > 0"
  3196   shows "\<forall> x. \<not>(\<exists> (e,c) \<in> set(\<rho> p). \<exists>(j::int) \<in> {1 .. c*d}. Ifm (a #bs) (\<sigma> p c (Add e (C j)))) \<longrightarrow> Ifm (real x#bs) p \<longrightarrow> Ifm (real (x - d)#bs) p" (is "\<forall> x. ?b x \<longrightarrow> ?P x \<longrightarrow> ?P (x - d)")
  3197 proof(clarify)
  3198   fix x 
  3199   assume nob1:"?b x" and px: "?P x" 
  3200   from iszlfm_gen[OF lp, rule_format, where y="real x"] have lp': "iszlfm p (real x#bs)".
  3201   have nob: "\<forall>(e, c)\<in>set (\<rho> p). \<forall>j\<in>{1..c * d}. real (c * x) \<noteq> Inum (real x # bs) e + real j" 
  3202   proof(clarify)
  3203     fix e c j assume ecR: "(e,c) \<in> set (\<rho> p)" and jD: "j\<in> {1 .. c*d}"
  3204       and cx: "real (c*x) = Inum (real x#bs) e + real j"
  3205     let ?e = "Inum (real x#bs) e"
  3206     let ?fe = "floor ?e"
  3207     from \<rho>_l[OF lp'] ecR have ei:"isint e (real x#bs)" and cp:"c>0" and nb:"numbound0 e"
  3208       by auto
  3209     from numbound0_gen [OF nb ei, rule_format,where y="a"] have "isint e (a#bs)" .
  3210     from cx ei[simplified isint_iff] have "real (c*x) = real (?fe + j)" by simp
  3211     hence cx: "c*x = ?fe + j" by (simp only: real_of_int_inject)
  3212     hence cdej:"c dvd ?fe + j" by (simp add: dvd_def) (rule_tac x="x" in exI, simp)
  3213     hence "real c rdvd real (?fe + j)" by (simp only: int_rdvd_iff)
  3214     hence rcdej: "real c rdvd ?e + real j" by (simp add: ei[simplified isint_iff])
  3215     from cx have "(c*x) div c = (?fe + j) div c" by simp
  3216     with cp have "x = (?fe + j) div c" by simp
  3217     with px have th: "?P ((?fe + j) div c)" by auto
  3218     from cp have cp': "real c > 0" by simp
  3219     from cdej have cdej': "c dvd floor (Inum (real x#bs) (Add e (C j)))" by simp
  3220     from nb have nb': "numbound0 (Add e (C j))" by simp
  3221     have ji: "isint (C j) (real x#bs)" by (simp add: isint_def)
  3222     from isint_add[OF ei ji] have ei':"isint (Add e (C j)) (real x#bs)" .
  3223     from th \<sigma>\<rho>[where b'="real x", OF lp' cp' nb' ei' cdej',symmetric]
  3224     have "Ifm (real x#bs) (\<sigma>\<rho> p (Add e (C j), c))" by simp
  3225     with rcdej have th: "Ifm (real x#bs) (\<sigma> p c (Add e (C j)))" by (simp add: \<sigma>_def)
  3226     from th bound0_I[OF \<sigma>_nb[OF lp nb', where k="c"],where bs="bs" and b="real x" and b'="a"]
  3227     have "Ifm (a#bs) (\<sigma> p c (Add e (C j)))" by blast
  3228       with ecR jD nob1    show "False" by blast
  3229   qed
  3230   from \<rho>[OF lp' px d dp nob] show "?P (x -d )" . 
  3231 qed
  3232 
  3233 
  3234 lemma rl_thm: 
  3235   assumes lp: "iszlfm p (real (i::int)#bs)"
  3236   shows "(\<exists> (x::int). Ifm (real x#bs) p) = ((\<exists> j\<in> {1 .. \<delta> p}. Ifm (real j#bs) (minusinf p)) \<or> (\<exists> (e,c) \<in> set (\<rho> p). \<exists> j\<in> {1 .. c*(\<delta> p)}. Ifm (a#bs) (\<sigma> p c (Add e (C j)))))"
  3237   (is "(\<exists>(x::int). ?P x) = ((\<exists> j\<in> {1.. \<delta> p}. ?MP j)\<or>(\<exists> (e,c) \<in> ?R. \<exists> j\<in> _. ?SP c e j))" 
  3238     is "?lhs = (?MD \<or> ?RD)"  is "?lhs = ?rhs")
  3239 proof-
  3240   let ?d= "\<delta> p"
  3241   from \<delta>[OF lp] have d:"d\<delta> p ?d" and dp: "?d > 0" by auto
  3242   { assume H:"?MD" hence th:"\<exists> (x::int). ?MP x" by blast
  3243     from H minusinf_ex[OF lp th] have ?thesis  by blast}
  3244   moreover
  3245   { fix e c j assume exR:"(e,c) \<in> ?R" and jD:"j\<in> {1 .. c*?d}" and spx:"?SP c e j"
  3246     from exR \<rho>_l[OF lp] have nb: "numbound0 e" and ei:"isint e (real i#bs)" and cp: "c > 0"
  3247       by auto
  3248     have "isint (C j) (real i#bs)" by (simp add: isint_iff)
  3249     with isint_add[OF numbound0_gen[OF nb ei,rule_format, where y="real i"]]
  3250     have eji:"isint (Add e (C j)) (real i#bs)" by simp
  3251     from nb have nb': "numbound0 (Add e (C j))" by simp
  3252     from spx bound0_I[OF \<sigma>_nb[OF lp nb', where k="c"], where bs="bs" and b="a" and b'="real i"]
  3253     have spx': "Ifm (real i # bs) (\<sigma> p c (Add e (C j)))" by blast
  3254     from spx' have rcdej:"real c rdvd (Inum (real i#bs) (Add e (C j)))" 
  3255       and sr:"Ifm (real i#bs) (\<sigma>\<rho> p (Add e (C j),c))" by (simp add: \<sigma>_def)+
  3256     from rcdej eji[simplified isint_iff] 
  3257     have "real c rdvd real (floor (Inum (real i#bs) (Add e (C j))))" by simp
  3258     hence cdej:"c dvd floor (Inum (real i#bs) (Add e (C j)))" by (simp only: int_rdvd_iff)
  3259     from cp have cp': "real c > 0" by simp
  3260     from \<sigma>\<rho>[OF lp cp' nb' eji cdej] spx' have "?P (\<lfloor>Inum (real i # bs) (Add e (C j))\<rfloor> div c)"
  3261       by (simp add: \<sigma>_def)
  3262     hence ?lhs by blast
  3263     with exR jD spx have ?thesis by blast}
  3264   moreover
  3265   { fix x assume px: "?P x" and nob: "\<not> ?RD"
  3266     from iszlfm_gen [OF lp,rule_format, where y="a"] have lp':"iszlfm p (a#bs)" .
  3267     from \<rho>'[OF lp' d dp, rule_format, OF nob] have th:"\<forall> x. ?P x \<longrightarrow> ?P (x - ?d)" by blast
  3268     from minusinf_inf[OF lp] obtain z where z:"\<forall> x<z. ?MP x = ?P x" by blast
  3269     have zp: "abs (x - z) + 1 \<ge> 0" by arith
  3270     from decr_lemma[OF dp,where x="x" and z="z"] 
  3271       decr_mult_lemma[OF dp th zp, rule_format, OF px] z have th:"\<exists> x. ?MP x" by auto
  3272     with minusinf_bex[OF lp] px nob have ?thesis by blast}
  3273   ultimately show ?thesis by blast
  3274 qed
  3275 
  3276 lemma mirror_\<alpha>\<rho>:   assumes lp: "iszlfm p (a#bs)"
  3277   shows "(\<lambda> (t,k). (Inum (a#bs) t, k)) ` set (\<alpha>\<rho> p) = (\<lambda> (t,k). (Inum (a#bs) t,k)) ` set (\<rho> (mirror p))"
  3278 using lp
  3279 by (induct p rule: mirror.induct, simp_all add: split_def image_Un )
  3280   
  3281 text {* The @{text "\<real>"} part*}
  3282 
  3283 text{* Linearity for fm where Bound 0 ranges over @{text "\<real>"}*}
  3284 consts
  3285   isrlfm :: "fm \<Rightarrow> bool"   (* Linearity test for fm *)
  3286 recdef isrlfm "measure size"
  3287   "isrlfm (And p q) = (isrlfm p \<and> isrlfm q)" 
  3288   "isrlfm (Or p q) = (isrlfm p \<and> isrlfm q)" 
  3289   "isrlfm (Eq  (CN 0 c e)) = (c>0 \<and> numbound0 e)"
  3290   "isrlfm (NEq (CN 0 c e)) = (c>0 \<and> numbound0 e)"
  3291   "isrlfm (Lt  (CN 0 c e)) = (c>0 \<and> numbound0 e)"
  3292   "isrlfm (Le  (CN 0 c e)) = (c>0 \<and> numbound0 e)"
  3293   "isrlfm (Gt  (CN 0 c e)) = (c>0 \<and> numbound0 e)"
  3294   "isrlfm (Ge  (CN 0 c e)) = (c>0 \<and> numbound0 e)"
  3295   "isrlfm p = (isatom p \<and> (bound0 p))"
  3296 
  3297 definition fp :: "fm \<Rightarrow> int \<Rightarrow> num \<Rightarrow> int \<Rightarrow> fm" where
  3298   "fp p n s j \<equiv> (if n > 0 then 
  3299             (And p (And (Ge (CN 0 n (Sub s (Add (Floor s) (C j)))))
  3300                         (Lt (CN 0 n (Sub s (Add (Floor s) (C (j+1))))))))
  3301             else 
  3302             (And p (And (Le (CN 0 (-n) (Add (Neg s) (Add (Floor s) (C j))))) 
  3303                         (Gt (CN 0 (-n) (Add (Neg s) (Add (Floor s) (C (j + 1)))))))))"
  3304 
  3305   (* splits the bounded from the unbounded part*)
  3306 function (sequential) rsplit0 :: "num \<Rightarrow> (fm \<times> int \<times> num) list" where
  3307   "rsplit0 (Bound 0) = [(T,1,C 0)]"
  3308 | "rsplit0 (Add a b) = (let acs = rsplit0 a ; bcs = rsplit0 b 
  3309               in map (\<lambda> ((p,n,t),(q,m,s)). (And p q, n+m, Add t s)) [(a,b). a\<leftarrow>acs,b\<leftarrow>bcs])"
  3310 | "rsplit0 (Sub a b) = rsplit0 (Add a (Neg b))"
  3311 | "rsplit0 (Neg a) = map (\<lambda> (p,n,s). (p,-n,Neg s)) (rsplit0 a)"
  3312 | "rsplit0 (Floor a) = concat (map 
  3313       (\<lambda> (p,n,s). if n=0 then [(p,0,Floor s)]
  3314           else (map (\<lambda> j. (fp p n s j, 0, Add (Floor s) (C j))) (if n > 0 then [0 .. n] else [n .. 0])))
  3315        (rsplit0 a))"
  3316 | "rsplit0 (CN 0 c a) = map (\<lambda> (p,n,s). (p,n+c,s)) (rsplit0 a)"
  3317 | "rsplit0 (CN m c a) = map (\<lambda> (p,n,s). (p,n,CN m c s)) (rsplit0 a)"
  3318 | "rsplit0 (CF c t s) = rsplit0 (Add (Mul c (Floor t)) s)"
  3319 | "rsplit0 (Mul c a) = map (\<lambda> (p,n,s). (p,c*n,Mul c s)) (rsplit0 a)"
  3320 | "rsplit0 t = [(T,0,t)]"
  3321 by pat_completeness auto
  3322 termination by (relation "measure num_size") auto
  3323 
  3324 lemma conj_rl[simp]: "isrlfm p \<Longrightarrow> isrlfm q \<Longrightarrow> isrlfm (conj p q)"
  3325   using conj_def by (cases p, auto)
  3326 lemma disj_rl[simp]: "isrlfm p \<Longrightarrow> isrlfm q \<Longrightarrow> isrlfm (disj p q)"
  3327   using disj_def by (cases p, auto)
  3328 
  3329 
  3330 lemma rsplit0_cs:
  3331   shows "\<forall> (p,n,s) \<in> set (rsplit0 t). 
  3332   (Ifm (x#bs) p \<longrightarrow>  (Inum (x#bs) t = Inum (x#bs) (CN 0 n s))) \<and> numbound0 s \<and> isrlfm p" 
  3333   (is "\<forall> (p,n,s) \<in> ?SS t. (?I p \<longrightarrow> ?N t = ?N (CN 0 n s)) \<and> _ \<and> _ ")
  3334 proof(induct t rule: rsplit0.induct)
  3335   case (5 a) 
  3336   let ?p = "\<lambda> (p,n,s) j. fp p n s j"
  3337   let ?f = "(\<lambda> (p,n,s) j. (?p (p,n,s) j, (0::int),Add (Floor s) (C j)))"
  3338   let ?J = "\<lambda> n. if n>0 then [0..n] else [n..0]"
  3339   let ?ff=" (\<lambda> (p,n,s). if n= 0 then [(p,0,Floor s)] else map (?f (p,n,s)) (?J n))"
  3340   have int_cases: "\<forall> (i::int). i= 0 \<or> i < 0 \<or> i > 0" by arith
  3341   have U1: "(UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). set (?ff (p,n,s)))) = 
  3342     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). set [(p,0,Floor s)]))" by auto
  3343   have U2': "\<forall> (p,n,s) \<in> {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0}. 
  3344     ?ff (p,n,s) = map (?f(p,n,s)) [0..n]" by auto
  3345   hence U2: "(UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). set (?ff (p,n,s)))) = 
  3346     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). 
  3347     set (map (?f(p,n,s)) [0..n])))"
  3348   proof-
  3349     fix M :: "('a\<times>'b\<times>'c) set" and f :: "('a\<times>'b\<times>'c) \<Rightarrow> 'd list" and g
  3350     assume "\<forall> (a,b,c) \<in> M. f (a,b,c) = g a b c"
  3351     thus "(UNION M (\<lambda> (a,b,c). set (f (a,b,c)))) = (UNION M (\<lambda> (a,b,c). set (g a b c)))"
  3352       by (auto simp add: split_def)
  3353   qed
  3354   have U3': "\<forall> (p,n,s) \<in> {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0}. ?ff (p,n,s) = map (?f(p,n,s)) [n..0]"
  3355     by auto
  3356   hence U3: "(UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s). set (?ff (p,n,s)))) = 
  3357     (UNION {(p,n,s). (p,n,s)\<in> ?SS a\<and>n<0} (\<lambda>(p,n,s). set (map (?f(p,n,s)) [n..0])))"
  3358       proof-
  3359     fix M :: "('a\<times>'b\<times>'c) set" and f :: "('a\<times>'b\<times>'c) \<Rightarrow> 'd list" and g
  3360     assume "\<forall> (a,b,c) \<in> M. f (a,b,c) = g a b c"
  3361     thus "(UNION M (\<lambda> (a,b,c). set (f (a,b,c)))) = (UNION M (\<lambda> (a,b,c). set (g a b c)))"
  3362       by (auto simp add: split_def)
  3363   qed
  3364   have "?SS (Floor a) = UNION (?SS a) (\<lambda>x. set (?ff x))"
  3365     by auto
  3366   also have "\<dots> = UNION (?SS a) (\<lambda> (p,n,s). set (?ff (p,n,s)))" by blast
  3367   also have "\<dots> = 
  3368     ((UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). set (?ff (p,n,s)))) Un 
  3369     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). set (?ff (p,n,s)))) Un 
  3370     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s). set (?ff (p,n,s)))))" 
  3371     using int_cases[rule_format] by blast
  3372   also have "\<dots> =  
  3373     ((UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). set [(p,0,Floor s)])) Un 
  3374    (UNION {(p,n,s). (p,n,s)\<in> ?SS a\<and>n>0} (\<lambda>(p,n,s). set(map(?f(p,n,s)) [0..n]))) Un 
  3375    (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s). 
  3376     set (map (?f(p,n,s)) [n..0]))))" by (simp only: U1 U2 U3)
  3377   also have "\<dots> =  
  3378     ((UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). {(p,0,Floor s)})) Un 
  3379     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). (?f(p,n,s)) ` {0 .. n})) Un 
  3380     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s). (?f(p,n,s)) ` {n .. 0})))"
  3381     by (simp only: set_map set_upto set.simps)
  3382   also have "\<dots> =   
  3383     ((UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). {(p,0,Floor s)})) Un 
  3384     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). {?f(p,n,s) j| j. j\<in> {0 .. n}})) Un 
  3385     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s).  {?f(p,n,s) j| j. j\<in> {n .. 0}})))" by blast
  3386   finally 
  3387   have FS: "?SS (Floor a) =   
  3388     ((UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). {(p,0,Floor s)})) Un 
  3389     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). {?f(p,n,s) j| j. j\<in> {0 .. n}})) Un 
  3390     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s).  {?f(p,n,s) j| j. j\<in> {n .. 0}})))"    by blast
  3391   show ?case
  3392   proof(simp only: FS, clarsimp simp del: Ifm.simps Inum.simps, -)
  3393     fix p n s
  3394     let ?ths = "(?I p \<longrightarrow> (?N (Floor a) = ?N (CN 0 n s))) \<and> numbound0 s \<and> isrlfm p"
  3395     assume "(\<exists>ba. (p, 0, ba) \<in> set (rsplit0 a) \<and> n = 0 \<and> s = Floor ba) \<or>
  3396        (\<exists>ab ac ba.
  3397            (ab, ac, ba) \<in> set (rsplit0 a) \<and>
  3398            0 < ac \<and>
  3399            (\<exists>j. p = fp ab ac ba j \<and>
  3400                 n = 0 \<and> s = Add (Floor ba) (C j) \<and> 0 \<le> j \<and> j \<le> ac)) \<or>
  3401        (\<exists>ab ac ba.
  3402            (ab, ac, ba) \<in> set (rsplit0 a) \<and>
  3403            ac < 0 \<and>
  3404            (\<exists>j. p = fp ab ac ba j \<and>
  3405                 n = 0 \<and> s = Add (Floor ba) (C j) \<and> ac \<le> j \<and> j \<le> 0))"
  3406     moreover 
  3407     { fix s'
  3408       assume "(p, 0, s') \<in> ?SS a" and "n = 0" and "s = Floor s'"
  3409       hence ?ths using 5(1) by auto }
  3410     moreover
  3411     { fix p' n' s' j
  3412       assume pns: "(p', n', s') \<in> ?SS a" 
  3413         and np: "0 < n'" 
  3414         and p_def: "p = ?p (p',n',s') j" 
  3415         and n0: "n = 0" 
  3416         and s_def: "s = (Add (Floor s') (C j))" 
  3417         and jp: "0 \<le> j" and jn: "j \<le> n'"
  3418       from 5 pns have H:"(Ifm ((x\<Colon>real) # (bs\<Colon>real list)) p' \<longrightarrow>
  3419           Inum (x # bs) a = Inum (x # bs) (CN 0 n' s')) \<and>
  3420           numbound0 s' \<and> isrlfm p'" by blast
  3421       hence nb: "numbound0 s'" by simp
  3422       from H have nf: "isrlfm (?p (p',n',s') j)" using fp_def np by (simp add: numsub_nb)
  3423       let ?nxs = "CN 0 n' s'"
  3424       let ?l = "floor (?N s') + j"
  3425       from H 
  3426       have "?I (?p (p',n',s') j) \<longrightarrow> 
  3427           (((?N ?nxs \<ge> real ?l) \<and> (?N ?nxs < real (?l + 1))) \<and> (?N a = ?N ?nxs ))" 
  3428         by (simp add: fp_def np algebra_simps numsub numadd numfloor)
  3429       also have "\<dots> \<longrightarrow> ((floor (?N ?nxs) = ?l) \<and> (?N a = ?N ?nxs ))"
  3430         using floor_int_eq[where x="?N ?nxs" and n="?l"] by simp
  3431       moreover
  3432       have "\<dots> \<longrightarrow> (?N (Floor a) = ?N ((Add (Floor s') (C j))))" by simp
  3433       ultimately have "?I (?p (p',n',s') j) \<longrightarrow> (?N (Floor a) = ?N ((Add (Floor s') (C j))))"
  3434         by blast
  3435       with s_def n0 p_def nb nf have ?ths by auto}
  3436     moreover
  3437     { fix p' n' s' j
  3438       assume pns: "(p', n', s') \<in> ?SS a" 
  3439         and np: "n' < 0" 
  3440         and p_def: "p = ?p (p',n',s') j" 
  3441         and n0: "n = 0" 
  3442         and s_def: "s = (Add (Floor s') (C j))" 
  3443         and jp: "n' \<le> j" and jn: "j \<le> 0"
  3444       from 5 pns have H:"(Ifm ((x\<Colon>real) # (bs\<Colon>real list)) p' \<longrightarrow>
  3445           Inum (x # bs) a = Inum (x # bs) (CN 0 n' s')) \<and>
  3446           numbound0 s' \<and> isrlfm p'" by blast
  3447       hence nb: "numbound0 s'" by simp
  3448       from H have nf: "isrlfm (?p (p',n',s') j)" using fp_def np by (simp add: numneg_nb)
  3449       let ?nxs = "CN 0 n' s'"
  3450       let ?l = "floor (?N s') + j"
  3451       from H 
  3452       have "?I (?p (p',n',s') j) \<longrightarrow> 
  3453           (((?N ?nxs \<ge> real ?l) \<and> (?N ?nxs < real (?l + 1))) \<and> (?N a = ?N ?nxs ))" 
  3454         by (simp add: np fp_def algebra_simps numneg numfloor numadd numsub)
  3455       also have "\<dots> \<longrightarrow> ((floor (?N ?nxs) = ?l) \<and> (?N a = ?N ?nxs ))"
  3456         using floor_int_eq[where x="?N ?nxs" and n="?l"] by simp
  3457       moreover
  3458       have "\<dots> \<longrightarrow> (?N (Floor a) = ?N ((Add (Floor s') (C j))))"  by simp
  3459       ultimately have "?I (?p (p',n',s') j) \<longrightarrow> (?N (Floor a) = ?N ((Add (Floor s') (C j))))"
  3460         by blast
  3461       with s_def n0 p_def nb nf have ?ths by auto}
  3462     ultimately show ?ths by auto
  3463   qed
  3464 next
  3465   case (3 a b) then show ?case
  3466     apply auto
  3467     apply (erule_tac x = "(aa, aaa, ba)" in ballE) apply simp_all
  3468     apply (erule_tac x = "(ab, ac, baa)" in ballE) apply simp_all
  3469     done
  3470 qed (auto simp add: Let_def split_def algebra_simps conj_rl)
  3471 
  3472 lemma real_in_int_intervals: 
  3473   assumes xb: "real m \<le> x \<and> x < real ((n::int) + 1)"
  3474   shows "\<exists> j\<in> {m.. n}. real j \<le> x \<and> x < real (j+1)" (is "\<exists> j\<in> ?N. ?P j")
  3475 by (rule bexI[where P="?P" and x="floor x" and A="?N"]) 
  3476 (auto simp add: floor_less_eq[where x="x" and a="n+1", simplified] xb[simplified] floor_mono[where x="real m" and y="x", OF conjunct1[OF xb], simplified floor_real_of_int[where n="m"]])
  3477 
  3478 lemma rsplit0_complete:
  3479   assumes xp:"0 \<le> x" and x1:"x < 1"
  3480   shows "\<exists> (p,n,s) \<in> set (rsplit0 t). Ifm (x#bs) p" (is "\<exists> (p,n,s) \<in> ?SS t. ?I p")
  3481 proof(induct t rule: rsplit0.induct)
  3482   case (2 a b) 
  3483   then have "\<exists> (pa,na,sa) \<in> ?SS a. ?I pa" by auto
  3484   then obtain "pa" "na" "sa" where pa: "(pa,na,sa)\<in> ?SS a \<and> ?I pa" by blast
  3485   with 2 have "\<exists> (pb,nb,sb) \<in> ?SS b. ?I pb" by blast
  3486   then obtain "pb" "nb" "sb" where pb: "(pb,nb,sb)\<in> ?SS b \<and> ?I pb" by blast
  3487   from pa pb have th: "((pa,na,sa),(pb,nb,sb)) \<in> set[(x,y). x\<leftarrow>rsplit0 a, y\<leftarrow>rsplit0 b]"
  3488     by (auto)
  3489   let ?f="(\<lambda> ((p,n,t),(q,m,s)). (And p q, n+m, Add t s))"
  3490   from imageI[OF th, where f="?f"] have "?f ((pa,na,sa),(pb,nb,sb)) \<in> ?SS (Add a b)"
  3491     by (simp add: Let_def)
  3492   hence "(And pa pb, na +nb, Add sa sb) \<in> ?SS (Add a b)" by simp
  3493   moreover from pa pb have "?I (And pa pb)" by simp
  3494   ultimately show ?case by blast
  3495 next
  3496   case (5 a) 
  3497   let ?p = "\<lambda> (p,n,s) j. fp p n s j"
  3498   let ?f = "(\<lambda> (p,n,s) j. (?p (p,n,s) j, (0::int),(Add (Floor s) (C j))))"
  3499   let ?J = "\<lambda> n. if n>0 then [0..n] else [n..0]"
  3500   let ?ff=" (\<lambda> (p,n,s). if n= 0 then [(p,0,Floor s)] else map (?f (p,n,s)) (?J n))"
  3501   have int_cases: "\<forall> (i::int). i= 0 \<or> i < 0 \<or> i > 0" by arith
  3502   have U1: "(UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). set (?ff (p,n,s)))) = (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). set [(p,0,Floor s)]))" by auto
  3503   have U2': "\<forall> (p,n,s) \<in> {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0}. ?ff (p,n,s) = map (?f(p,n,s)) [0..n]"
  3504     by auto
  3505   hence U2: "(UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). set (?ff (p,n,s)))) = (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). set (map (?f(p,n,s)) [0..n])))"
  3506   proof-
  3507     fix M :: "('a\<times>'b\<times>'c) set" and f :: "('a\<times>'b\<times>'c) \<Rightarrow> 'd list" and g
  3508     assume "\<forall> (a,b,c) \<in> M. f (a,b,c) = g a b c"
  3509     thus "(UNION M (\<lambda> (a,b,c). set (f (a,b,c)))) = (UNION M (\<lambda> (a,b,c). set (g a b c)))"
  3510       by (auto simp add: split_def)
  3511   qed
  3512   have U3': "\<forall> (p,n,s) \<in> {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0}. ?ff (p,n,s) = map (?f(p,n,s)) [n..0]"
  3513     by auto
  3514   hence U3: "(UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s). set (?ff (p,n,s)))) = (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s). set (map (?f(p,n,s)) [n..0])))"
  3515   proof-
  3516     fix M :: "('a\<times>'b\<times>'c) set" and f :: "('a\<times>'b\<times>'c) \<Rightarrow> 'd list" and g
  3517     assume "\<forall> (a,b,c) \<in> M. f (a,b,c) = g a b c"
  3518     thus "(UNION M (\<lambda> (a,b,c). set (f (a,b,c)))) = (UNION M (\<lambda> (a,b,c). set (g a b c)))"
  3519       by (auto simp add: split_def)
  3520   qed
  3521 
  3522   have "?SS (Floor a) = UNION (?SS a) (\<lambda>x. set (?ff x))" by auto
  3523   also have "\<dots> = UNION (?SS a) (\<lambda> (p,n,s). set (?ff (p,n,s)))" by blast
  3524   also have "\<dots> = 
  3525     ((UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). set (?ff (p,n,s)))) Un 
  3526     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). set (?ff (p,n,s)))) Un 
  3527     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s). set (?ff (p,n,s)))))" 
  3528     using int_cases[rule_format] by blast
  3529   also have "\<dots> =  
  3530     ((UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). set [(p,0,Floor s)])) Un 
  3531     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). set (map (?f(p,n,s)) [0..n]))) Un 
  3532     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s). set (map (?f(p,n,s)) [n..0]))))" by (simp only: U1 U2 U3)
  3533   also have "\<dots> =  
  3534     ((UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). {(p,0,Floor s)})) Un 
  3535     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). (?f(p,n,s)) ` {0 .. n})) Un 
  3536     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s). (?f(p,n,s)) ` {n .. 0})))"
  3537     by (simp only: set_map set_upto set.simps)
  3538   also have "\<dots> =   
  3539     ((UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). {(p,0,Floor s)})) Un 
  3540     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). {?f(p,n,s) j| j. j\<in> {0 .. n}})) Un 
  3541     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s).  {?f(p,n,s) j| j. j\<in> {n .. 0}})))" by blast
  3542   finally 
  3543   have FS: "?SS (Floor a) =   
  3544     ((UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n=0} (\<lambda> (p,n,s). {(p,0,Floor s)})) Un 
  3545     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n>0} (\<lambda> (p,n,s). {?f(p,n,s) j| j. j\<in> {0 .. n}})) Un 
  3546     (UNION {(p,n,s). (p,n,s) \<in> ?SS a \<and> n<0} (\<lambda> (p,n,s).  {?f(p,n,s) j| j. j\<in> {n .. 0}})))"
  3547     by blast
  3548   from 5 have "\<exists> (p,n,s) \<in> ?SS a. ?I p" by auto
  3549   then obtain "p" "n" "s" where pns: "(p,n,s) \<in> ?SS a \<and> ?I p" by blast
  3550   let ?N = "\<lambda> t. Inum (x#bs) t"
  3551   from rsplit0_cs[rule_format] pns have ans:"(?N a = ?N (CN 0 n s)) \<and> numbound0 s \<and> isrlfm p"
  3552     by auto
  3553   
  3554   have "n=0 \<or> n >0 \<or> n <0" by arith
  3555   moreover {assume "n=0" hence ?case using pns by (simp only: FS) auto }
  3556   moreover
  3557   {
  3558     assume np: "n > 0"
  3559     from real_of_int_floor_le[where r="?N s"] have "?N (Floor s) \<le> ?N s" by simp
  3560     also from mult_left_mono[OF xp] np have "?N s \<le> real n * x + ?N s" by simp
  3561     finally have "?N (Floor s) \<le> real n * x + ?N s" .
  3562     moreover
  3563     {from x1 np have "real n *x + ?N s < real n + ?N s" by simp
  3564       also from real_of_int_floor_add_one_gt[where r="?N s"] 
  3565       have "\<dots> < real n + ?N (Floor s) + 1" by simp
  3566       finally have "real n *x + ?N s < ?N (Floor s) + real (n+1)" by simp}
  3567     ultimately have "?N (Floor s) \<le> real n *x + ?N s\<and> real n *x + ?N s < ?N (Floor s) + real (n+1)" by simp
  3568     hence th: "0 \<le> real n *x + ?N s - ?N (Floor s) \<and> real n *x + ?N s - ?N (Floor s) < real (n+1)" by simp
  3569     from real_in_int_intervals th have  "\<exists> j\<in> {0 .. n}. real j \<le> real n *x + ?N s - ?N (Floor s)\<and> real n *x + ?N s - ?N (Floor s) < real (j+1)" by simp
  3570     
  3571     hence "\<exists> j\<in> {0 .. n}. 0 \<le> real n *x + ?N s - ?N (Floor s) - real j \<and> real n *x + ?N s - ?N (Floor s) - real (j+1) < 0"
  3572       by(simp only: myle[of _ "real n * x + Inum (x # bs) s - Inum (x # bs) (Floor s)"] less_iff_diff_less_0[where a="real n *x + ?N s - ?N (Floor s)"]) 
  3573     hence "\<exists> j\<in> {0.. n}. ?I (?p (p,n,s) j)"
  3574       using pns by (simp add: fp_def np algebra_simps numsub numadd)
  3575     then obtain "j" where j_def: "j\<in> {0 .. n} \<and> ?I (?p (p,n,s) j)" by blast
  3576     hence "\<exists>x \<in> {?p (p,n,s) j |j. 0\<le> j \<and> j \<le> n }. ?I x" by auto
  3577     hence ?case using pns 
  3578       by (simp only: FS,simp add: bex_Un) 
  3579     (rule disjI2, rule disjI1,rule exI [where x="p"],
  3580       rule exI [where x="n"],rule exI [where x="s"],simp_all add: np)
  3581   }
  3582   moreover
  3583   { assume nn: "n < 0" hence np: "-n >0" by simp
  3584     from real_of_int_floor_le[where r="?N s"] have "?N (Floor s) + 1 > ?N s" by simp
  3585     moreover from mult_left_mono_neg[OF xp] nn have "?N s \<ge> real n * x + ?N s" by simp
  3586     ultimately have "?N (Floor s) + 1 > real n * x + ?N s" by arith 
  3587     moreover
  3588     {from x1 nn have "real n *x + ?N s \<ge> real n + ?N s" by simp
  3589       moreover from real_of_int_floor_le[where r="?N s"]  have "real n + ?N s \<ge> real n + ?N (Floor s)" by simp
  3590       ultimately have "real n *x + ?N s \<ge> ?N (Floor s) + real n" 
  3591         by (simp only: algebra_simps)}
  3592     ultimately have "?N (Floor s) + real n \<le> real n *x + ?N s\<and> real n *x + ?N s < ?N (Floor s) + real (1::int)" by simp
  3593     hence th: "real n \<le> real n *x + ?N s - ?N (Floor s) \<and> real n *x + ?N s - ?N (Floor s) < real (1::int)" by simp
  3594     have th1: "\<forall> (a::real). (- a > 0) = (a < 0)" by auto
  3595     have th2: "\<forall> (a::real). (0 \<ge> - a) = (a \<ge> 0)" by auto
  3596     from real_in_int_intervals th  have  "\<exists> j\<in> {n .. 0}. real j \<le> real n *x + ?N s - ?N (Floor s)\<and> real n *x + ?N s - ?N (Floor s) < real (j+1)" by simp
  3597     
  3598     hence "\<exists> j\<in> {n .. 0}. 0 \<le> real n *x + ?N s - ?N (Floor s) - real j \<and> real n *x + ?N s - ?N (Floor s) - real (j+1) < 0"
  3599       by(simp only: myle[of _ "real n * x + Inum (x # bs) s - Inum (x # bs) (Floor s)"] less_iff_diff_less_0[where a="real n *x + ?N s - ?N (Floor s)"]) 
  3600     hence "\<exists> j\<in> {n .. 0}. 0 \<ge> - (real n *x + ?N s - ?N (Floor s) - real j) \<and> - (real n *x + ?N s - ?N (Floor s) - real (j+1)) > 0" by (simp only: th1[rule_format] th2[rule_format])
  3601     hence "\<exists> j\<in> {n.. 0}. ?I (?p (p,n,s) j)"
  3602       using pns by (simp add: fp_def nn diff_minus add_ac mult_ac numfloor numadd numneg
  3603         del: diff_less_0_iff_less diff_le_0_iff_le) 
  3604     then obtain "j" where j_def: "j\<in> {n .. 0} \<and> ?I (?p (p,n,s) j)" by blast
  3605     hence "\<exists>x \<in> {?p (p,n,s) j |j. n\<le> j \<and> j \<le> 0 }. ?I x" by auto
  3606     hence ?case using pns 
  3607       by (simp only: FS,simp add: bex_Un)
  3608     (rule disjI2, rule disjI2,rule exI [where x="p"],
  3609       rule exI [where x="n"],rule exI [where x="s"],simp_all add: nn)
  3610   }
  3611   ultimately show ?case by blast
  3612 qed (auto simp add: Let_def split_def)
  3613 
  3614     (* Linearize a formula where Bound 0 ranges over [0,1) *)
  3615 
  3616 definition rsplit :: "(int \<Rightarrow> num \<Rightarrow> fm) \<Rightarrow> num \<Rightarrow> fm" where
  3617   "rsplit f a \<equiv> foldr disj (map (\<lambda> (\<phi>, n, s). conj \<phi> (f n s)) (rsplit0 a)) F"
  3618 
  3619 lemma foldr_disj_map: "Ifm bs (foldr disj (map f xs) F) = (\<exists> x \<in> set xs. Ifm bs (f x))"
  3620 by(induct xs, simp_all)
  3621 
  3622 lemma foldr_conj_map: "Ifm bs (foldr conj (map f xs) T) = (\<forall> x \<in> set xs. Ifm bs (f x))"
  3623 by(induct xs, simp_all)
  3624 
  3625 lemma foldr_disj_map_rlfm: 
  3626   assumes lf: "\<forall> n s. numbound0 s \<longrightarrow> isrlfm (f n s)"
  3627   and \<phi>: "\<forall> (\<phi>,n,s) \<in> set xs. numbound0 s \<and> isrlfm \<phi>"
  3628   shows "isrlfm (foldr disj (map (\<lambda> (\<phi>, n, s). conj \<phi> (f n s)) xs) F)"
  3629 using lf \<phi> by (induct xs, auto)
  3630 
  3631 lemma rsplit_ex: "Ifm bs (rsplit f a) = (\<exists> (\<phi>,n,s) \<in> set (rsplit0 a). Ifm bs (conj \<phi> (f n s)))"
  3632 using foldr_disj_map[where xs="rsplit0 a"] rsplit_def by (simp add: split_def)
  3633 
  3634 lemma rsplit_l: assumes lf: "\<forall> n s. numbound0 s \<longrightarrow> isrlfm (f n s)"
  3635   shows "isrlfm (rsplit f a)"
  3636 proof-
  3637   from rsplit0_cs[where t="a"] have th: "\<forall> (\<phi>,n,s) \<in> set (rsplit0 a). numbound0 s \<and> isrlfm \<phi>" by blast
  3638   from foldr_disj_map_rlfm[OF lf th] rsplit_def show ?thesis by simp
  3639 qed
  3640 
  3641 lemma rsplit: 
  3642   assumes xp: "x \<ge> 0" and x1: "x < 1"
  3643   and f: "\<forall> a n s. Inum (x#bs) a = Inum (x#bs) (CN 0 n s) \<and> numbound0 s \<longrightarrow> (Ifm (x#bs) (f n s) = Ifm (x#bs) (g a))"
  3644   shows "Ifm (x#bs) (rsplit f a) = Ifm (x#bs) (g a)"
  3645 proof(auto)
  3646   let ?I = "\<lambda>x p. Ifm (x#bs) p"
  3647   let ?N = "\<lambda> x t. Inum (x#bs) t"
  3648   assume "?I x (rsplit f a)"
  3649   hence "\<exists> (\<phi>,n,s) \<in> set (rsplit0 a). ?I x (And \<phi> (f n s))" using rsplit_ex by simp
  3650   then obtain "\<phi>" "n" "s" where fnsS:"(\<phi>,n,s) \<in> set (rsplit0 a)" and "?I x (And \<phi> (f n s))" by blast
  3651   hence \<phi>: "?I x \<phi>" and fns: "?I x (f n s)" by auto
  3652   from rsplit0_cs[where t="a" and bs="bs" and x="x", rule_format, OF fnsS] \<phi> 
  3653   have th: "(?N x a = ?N x (CN 0 n s)) \<and> numbound0 s" by auto
  3654   from f[rule_format, OF th] fns show "?I x (g a)" by simp
  3655 next
  3656   let ?I = "\<lambda>x p. Ifm (x#bs) p"
  3657   let ?N = "\<lambda> x t. Inum (x#bs) t"
  3658   assume ga: "?I x (g a)"
  3659   from rsplit0_complete[OF xp x1, where bs="bs" and t="a"] 
  3660   obtain "\<phi>" "n" "s" where fnsS:"(\<phi>,n,s) \<in> set (rsplit0 a)" and fx: "?I x \<phi>" by blast
  3661   from rsplit0_cs[where t="a" and x="x" and bs="bs"] fnsS fx
  3662   have ans: "?N x a = ?N x (CN 0 n s)" and nb: "numbound0 s" by auto
  3663   with ga f have "?I x (f n s)" by auto
  3664   with rsplit_ex fnsS fx show "?I x (rsplit f a)" by auto
  3665 qed
  3666 
  3667 definition lt :: "int \<Rightarrow> num \<Rightarrow> fm" where
  3668   lt_def: "lt c t = (if c = 0 then (Lt t) else if c > 0 then (Lt (CN 0 c t)) 
  3669                         else (Gt (CN 0 (-c) (Neg t))))"
  3670 
  3671 definition  le :: "int \<Rightarrow> num \<Rightarrow> fm" where
  3672   le_def: "le c t = (if c = 0 then (Le t) else if c > 0 then (Le (CN 0 c t)) 
  3673                         else (Ge (CN 0 (-c) (Neg t))))"
  3674 
  3675 definition  gt :: "int \<Rightarrow> num \<Rightarrow> fm" where
  3676   gt_def: "gt c t = (if c = 0 then (Gt t) else if c > 0 then (Gt (CN 0 c t)) 
  3677                         else (Lt (CN 0 (-c) (Neg t))))"
  3678 
  3679 definition  ge :: "int \<Rightarrow> num \<Rightarrow> fm" where
  3680   ge_def: "ge c t = (if c = 0 then (Ge t) else if c > 0 then (Ge (CN 0 c t)) 
  3681                         else (Le (CN 0 (-c) (Neg t))))"
  3682 
  3683 definition  eq :: "int \<Rightarrow> num \<Rightarrow> fm" where
  3684   eq_def: "eq c t = (if c = 0 then (Eq t) else if c > 0 then (Eq (CN 0 c t)) 
  3685                         else (Eq (CN 0 (-c) (Neg t))))"
  3686 
  3687 definition neq :: "int \<Rightarrow> num \<Rightarrow> fm" where
  3688   neq_def: "neq c t = (if c = 0 then (NEq t) else if c > 0 then (NEq (CN 0 c t)) 
  3689                         else (NEq (CN 0 (-c) (Neg t))))"
  3690 
  3691 lemma lt_mono: "\<forall> a n s. Inum (x#bs) a = Inum (x#bs) (CN 0 n s) \<and> numbound0 s \<longrightarrow> Ifm (x#bs) (lt n s) = Ifm (x#bs) (Lt a)"
  3692   (is "\<forall> a n s . ?N a = ?N (CN 0 n s) \<and> _\<longrightarrow> ?I (lt n s) = ?I (Lt a)")
  3693 proof(clarify)
  3694   fix a n s
  3695   assume H: "?N a = ?N (CN 0 n s)"
  3696   show "?I (lt n s) = ?I (Lt a)" using H by (cases "n=0", (simp add: lt_def))
  3697   (cases "n > 0", simp_all add: lt_def algebra_simps myless[of _ "0"])
  3698 qed
  3699 
  3700 lemma lt_l: "isrlfm (rsplit lt a)"
  3701   by (rule rsplit_l[where f="lt" and a="a"], auto simp add: lt_def,
  3702     case_tac s, simp_all, case_tac "nat", simp_all)
  3703 
  3704 lemma le_mono: "\<forall> a n s. Inum (x#bs) a = Inum (x#bs) (CN 0 n s) \<and> numbound0 s \<longrightarrow> Ifm (x#bs) (le n s) = Ifm (x#bs) (Le a)" (is "\<forall> a n s. ?N a = ?N (CN 0 n s) \<and> _ \<longrightarrow> ?I (le n s) = ?I (Le a)")
  3705 proof(clarify)
  3706   fix a n s
  3707   assume H: "?N a = ?N (CN 0 n s)"
  3708   show "?I (le n s) = ?I (Le a)" using H by (cases "n=0", (simp add: le_def))
  3709   (cases "n > 0", simp_all add: le_def algebra_simps myle[of _ "0"])
  3710 qed
  3711 
  3712 lemma le_l: "isrlfm (rsplit le a)"
  3713   by (rule rsplit_l[where f="le" and a="a"], auto simp add: le_def) 
  3714 (case_tac s, simp_all, case_tac "nat",simp_all)
  3715 
  3716 lemma gt_mono: "\<forall> a n s. Inum (x#bs) a = Inum (x#bs) (CN 0 n s) \<and> numbound0 s \<longrightarrow> Ifm (x#bs) (gt n s) = Ifm (x#bs) (Gt a)" (is "\<forall> a n s. ?N a = ?N (CN 0 n s) \<and> _ \<longrightarrow> ?I (gt n s) = ?I (Gt a)")
  3717 proof(clarify)
  3718   fix a n s
  3719   assume H: "?N a = ?N (CN 0 n s)"
  3720   show "?I (gt n s) = ?I (Gt a)" using H by (cases "n=0", (simp add: gt_def))
  3721   (cases "n > 0", simp_all add: gt_def algebra_simps myless[of _ "0"])
  3722 qed
  3723 lemma gt_l: "isrlfm (rsplit gt a)"
  3724   by (rule rsplit_l[where f="gt" and a="a"], auto simp add: gt_def) 
  3725 (case_tac s, simp_all, case_tac "nat", simp_all)
  3726 
  3727 lemma ge_mono: "\<forall> a n s. Inum (x#bs) a = Inum (x#bs) (CN 0 n s) \<and> numbound0 s \<longrightarrow> Ifm (x#bs) (ge n s) = Ifm (x#bs) (Ge a)" (is "\<forall> a n s . ?N a = ?N (CN 0 n s) \<and> _ \<longrightarrow> ?I (ge n s) = ?I (Ge a)")
  3728 proof(clarify)
  3729   fix a n s 
  3730   assume H: "?N a = ?N (CN 0 n s)"
  3731   show "?I (ge n s) = ?I (Ge a)" using H by (cases "n=0", (simp add: ge_def))
  3732   (cases "n > 0", simp_all add: ge_def algebra_simps myle[of _ "0"])
  3733 qed
  3734 lemma ge_l: "isrlfm (rsplit ge a)"
  3735   by (rule rsplit_l[where f="ge" and a="a"], auto simp add: ge_def) 
  3736 (case_tac s, simp_all, case_tac "nat", simp_all)
  3737 
  3738 lemma eq_mono: "\<forall> a n s. Inum (x#bs) a = Inum (x#bs) (CN 0 n s) \<and> numbound0 s \<longrightarrow> Ifm (x#bs) (eq n s) = Ifm (x#bs) (Eq a)" (is "\<forall> a n s. ?N a = ?N (CN 0 n s) \<and> _ \<longrightarrow> ?I (eq n s) = ?I (Eq a)")
  3739 proof(clarify)
  3740   fix a n s 
  3741   assume H: "?N a = ?N (CN 0 n s)"
  3742   show "?I (eq n s) = ?I (Eq a)" using H by (auto simp add: eq_def algebra_simps)
  3743 qed
  3744 lemma eq_l: "isrlfm (rsplit eq a)"
  3745   by (rule rsplit_l[where f="eq" and a="a"], auto simp add: eq_def) 
  3746 (case_tac s, simp_all, case_tac"nat", simp_all)
  3747 
  3748 lemma neq_mono: "\<forall> a n s. Inum (x#bs) a = Inum (x#bs) (CN 0 n s) \<and> numbound0 s \<longrightarrow> Ifm (x#bs) (neq n s) = Ifm (x#bs) (NEq a)" (is "\<forall> a n s. ?N a = ?N (CN 0 n s) \<and> _ \<longrightarrow> ?I (neq n s) = ?I (NEq a)")
  3749 proof(clarify)
  3750   fix a n s bs
  3751   assume H: "?N a = ?N (CN 0 n s)"
  3752   show "?I (neq n s) = ?I (NEq a)" using H by (auto simp add: neq_def algebra_simps)
  3753 qed
  3754 
  3755 lemma neq_l: "isrlfm (rsplit neq a)"
  3756   by (rule rsplit_l[where f="neq" and a="a"], auto simp add: neq_def) 
  3757 (case_tac s, simp_all, case_tac"nat", simp_all)
  3758 
  3759 lemma small_le: 
  3760   assumes u0:"0 \<le> u" and u1: "u < 1"
  3761   shows "(-u \<le> real (n::int)) = (0 \<le> n)"
  3762 using u0 u1  by auto
  3763 
  3764 lemma small_lt: 
  3765   assumes u0:"0 \<le> u" and u1: "u < 1"
  3766   shows "(real (n::int) < real (m::int) - u) = (n < m)"
  3767 using u0 u1  by auto
  3768 
  3769 lemma rdvd01_cs: 
  3770   assumes up: "u \<ge> 0" and u1: "u<1" and np: "real n > 0"
  3771   shows "(real (i::int) rdvd real (n::int) * u - s) = (\<exists> j\<in> {0 .. n - 1}. real n * u = s - real (floor s) + real j \<and> real i rdvd real (j - floor s))" (is "?lhs = ?rhs")
  3772 proof-
  3773   let ?ss = "s - real (floor s)"
  3774   from real_of_int_floor_add_one_gt[where r="s", simplified myless[of "s"]] 
  3775     real_of_int_floor_le[where r="s"]  have ss0:"?ss \<ge> 0" and ss1:"?ss < 1" 
  3776     by (auto simp add: myle[of _ "s", symmetric] myless[of "?ss"])
  3777   from np have n0: "real n \<ge> 0" by simp
  3778   from mult_left_mono[OF up n0] mult_strict_left_mono[OF u1 np] 
  3779   have nu0:"real n * u - s \<ge> -s" and nun:"real n * u -s < real n - s" by auto  
  3780   from int_rdvd_real[where i="i" and x="real (n::int) * u - s"] 
  3781   have "real i rdvd real n * u - s = 
  3782     (i dvd floor (real n * u -s) \<and> (real (floor (real n * u - s)) = real n * u - s ))" 
  3783     (is "_ = (?DE)" is "_ = (?D \<and> ?E)") by simp
  3784   also have "\<dots> = (?DE \<and> real(floor (real n * u - s) + floor s)\<ge> -?ss 
  3785     \<and> real(floor (real n * u - s) + floor s)< real n - ?ss)" (is "_=(?DE \<and>real ?a \<ge> _ \<and> real ?a < _)")
  3786     using nu0 nun  by auto
  3787   also have "\<dots> = (?DE \<and> ?a \<ge> 0 \<and> ?a < n)" by(simp only: small_le[OF ss0 ss1] small_lt[OF ss0 ss1])
  3788   also have "\<dots> = (?DE \<and> (\<exists> j\<in> {0 .. (n - 1)}. ?a = j))" by simp
  3789   also have "\<dots> = (?DE \<and> (\<exists> j\<in> {0 .. (n - 1)}. real (\<lfloor>real n * u - s\<rfloor>) = real j - real \<lfloor>s\<rfloor> ))"
  3790     by (simp only: algebra_simps real_of_int_diff[symmetric] real_of_int_inject del: real_of_int_diff)
  3791   also have "\<dots> = ((\<exists> j\<in> {0 .. (n - 1)}. real n * u - s = real j - real \<lfloor>s\<rfloor> \<and> real i rdvd real n * u - s))" using int_rdvd_iff[where i="i" and t="\<lfloor>real n * u - s\<rfloor>"]
  3792     by (auto cong: conj_cong)
  3793   also have "\<dots> = ?rhs" by(simp cong: conj_cong) (simp add: algebra_simps )
  3794   finally show ?thesis .
  3795 qed
  3796 
  3797 definition
  3798   DVDJ:: "int \<Rightarrow> int \<Rightarrow> num \<Rightarrow> fm"
  3799 where
  3800   DVDJ_def: "DVDJ i n s = (foldr disj (map (\<lambda> j. conj (Eq (CN 0 n (Add s (Sub (Floor (Neg s)) (C j))))) (Dvd i (Sub (C j) (Floor (Neg s))))) [0..n - 1]) F)"
  3801 
  3802 definition
  3803   NDVDJ:: "int \<Rightarrow> int \<Rightarrow> num \<Rightarrow> fm"
  3804 where
  3805   NDVDJ_def: "NDVDJ i n s = (foldr conj (map (\<lambda> j. disj (NEq (CN 0 n (Add s (Sub (Floor (Neg s)) (C j))))) (NDvd i (Sub (C j) (Floor (Neg s))))) [0..n - 1]) T)"
  3806 
  3807 lemma DVDJ_DVD: 
  3808   assumes xp:"x\<ge> 0" and x1: "x < 1" and np:"real n > 0"
  3809   shows "Ifm (x#bs) (DVDJ i n s) = Ifm (x#bs) (Dvd i (CN 0 n s))"
  3810 proof-
  3811   let ?f = "\<lambda> j. conj (Eq(CN 0 n (Add s (Sub(Floor (Neg s)) (C j))))) (Dvd i (Sub (C j) (Floor (Neg s))))"
  3812   let ?s= "Inum (x#bs) s"
  3813   from foldr_disj_map[where xs="[0..n - 1]" and bs="x#bs" and f="?f"]
  3814   have "Ifm (x#bs) (DVDJ i n s) = (\<exists> j\<in> {0 .. (n - 1)}. Ifm (x#bs) (?f j))" 
  3815     by (simp add: np DVDJ_def)
  3816   also have "\<dots> = (\<exists> j\<in> {0 .. (n - 1)}. real n * x = (- ?s) - real (floor (- ?s)) + real j \<and> real i rdvd real (j - floor (- ?s)))" by (simp add: algebra_simps diff_minus[symmetric])
  3817   also from rdvd01_cs[OF xp x1 np, where i="i" and s="-?s"] 
  3818   have "\<dots> = (real i rdvd real n * x - (-?s))" by simp
  3819   finally show ?thesis by simp
  3820 qed
  3821 
  3822 lemma NDVDJ_NDVD: 
  3823   assumes xp:"x\<ge> 0" and x1: "x < 1" and np:"real n > 0"
  3824   shows "Ifm (x#bs) (NDVDJ i n s) = Ifm (x#bs) (NDvd i (CN 0 n s))"
  3825 proof-
  3826   let ?f = "\<lambda> j. disj(NEq(CN 0 n (Add s (Sub (Floor (Neg s)) (C j))))) (NDvd i (Sub (C j) (Floor(Neg s))))"
  3827   let ?s= "Inum (x#bs) s"
  3828   from foldr_conj_map[where xs="[0..n - 1]" and bs="x#bs" and f="?f"]
  3829   have "Ifm (x#bs) (NDVDJ i n s) = (\<forall> j\<in> {0 .. (n - 1)}. Ifm (x#bs) (?f j))" 
  3830     by (simp add: np NDVDJ_def)
  3831   also have "\<dots> = (\<not> (\<exists> j\<in> {0 .. (n - 1)}. real n * x = (- ?s) - real (floor (- ?s)) + real j \<and> real i rdvd real (j - floor (- ?s))))" by (simp add: algebra_simps diff_minus[symmetric])
  3832   also from rdvd01_cs[OF xp x1 np, where i="i" and s="-?s"] 
  3833   have "\<dots> = (\<not> (real i rdvd real n * x - (-?s)))" by simp
  3834   finally show ?thesis by simp
  3835 qed  
  3836 
  3837 lemma foldr_disj_map_rlfm2: 
  3838   assumes lf: "\<forall> n . isrlfm (f n)"
  3839   shows "isrlfm (foldr disj (map f xs) F)"
  3840 using lf by (induct xs, auto)
  3841 lemma foldr_And_map_rlfm2: 
  3842   assumes lf: "\<forall> n . isrlfm (f n)"
  3843   shows "isrlfm (foldr conj (map f xs) T)"
  3844 using lf by (induct xs, auto)
  3845 
  3846 lemma DVDJ_l: assumes ip: "i >0" and np: "n>0" and nb: "numbound0 s"
  3847   shows "isrlfm (DVDJ i n s)"
  3848 proof-
  3849   let ?f="\<lambda>j. conj (Eq (CN 0 n (Add s (Sub (Floor (Neg s)) (C j)))))
  3850                          (Dvd i (Sub (C j) (Floor (Neg s))))"
  3851   have th: "\<forall> j. isrlfm (?f j)" using nb np by auto
  3852   from DVDJ_def foldr_disj_map_rlfm2[OF th] show ?thesis by simp 
  3853 qed
  3854 
  3855 lemma NDVDJ_l: assumes ip: "i >0" and np: "n>0" and nb: "numbound0 s"
  3856   shows "isrlfm (NDVDJ i n s)"
  3857 proof-
  3858   let ?f="\<lambda>j. disj (NEq (CN 0 n (Add s (Sub (Floor (Neg s)) (C j)))))
  3859                       (NDvd i (Sub (C j) (Floor (Neg s))))"
  3860   have th: "\<forall> j. isrlfm (?f j)" using nb np by auto
  3861   from NDVDJ_def foldr_And_map_rlfm2[OF th] show ?thesis by auto
  3862 qed
  3863 
  3864 definition DVD :: "int \<Rightarrow> int \<Rightarrow> num \<Rightarrow> fm" where
  3865   DVD_def: "DVD i c t =
  3866   (if i=0 then eq c t else 
  3867   if c = 0 then (Dvd i t) else if c >0 then DVDJ (abs i) c t else DVDJ (abs i) (-c) (Neg t))"
  3868 
  3869 definition  NDVD :: "int \<Rightarrow> int \<Rightarrow> num \<Rightarrow> fm" where
  3870   "NDVD i c t =
  3871   (if i=0 then neq c t else 
  3872   if c = 0 then (NDvd i t) else if c >0 then NDVDJ (abs i) c t else NDVDJ (abs i) (-c) (Neg t))"
  3873 
  3874 lemma DVD_mono: 
  3875   assumes xp: "0\<le> x" and x1: "x < 1" 
  3876   shows "\<forall> a n s. Inum (x#bs) a = Inum (x#bs) (CN 0 n s) \<and> numbound0 s \<longrightarrow> Ifm (x#bs) (DVD i n s) = Ifm (x#bs) (Dvd i a)"
  3877   (is "\<forall> a n s. ?N a = ?N (CN 0 n s) \<and> _ \<longrightarrow> ?I (DVD i n s) = ?I (Dvd i a)")
  3878 proof(clarify)
  3879   fix a n s 
  3880   assume H: "?N a = ?N (CN 0 n s)" and nb: "numbound0 s"
  3881   let ?th = "?I (DVD i n s) = ?I (Dvd i a)"
  3882   have "i=0 \<or> (i\<noteq>0 \<and> n=0) \<or> (i\<noteq>0 \<and> n < 0) \<or> (i\<noteq>0 \<and> n > 0)" by arith
  3883   moreover {assume iz: "i=0" hence ?th using eq_mono[rule_format, OF conjI[OF H nb]] 
  3884       by (simp add: DVD_def rdvd_left_0_eq)}
  3885   moreover {assume inz: "i\<noteq>0" and "n=0" hence ?th by (simp add: H DVD_def) } 
  3886   moreover {assume inz: "i\<noteq>0" and "n<0" hence ?th 
  3887       by (simp add: DVD_def H DVDJ_DVD[OF xp x1] rdvd_abs1 
  3888         rdvd_minus[where d="i" and t="real n * x + Inum (x # bs) s"]) } 
  3889   moreover {assume inz: "i\<noteq>0" and "n>0" hence ?th by (simp add:DVD_def H DVDJ_DVD[OF xp x1] rdvd_abs1)}
  3890   ultimately show ?th by blast
  3891 qed
  3892 
  3893 lemma NDVD_mono:   assumes xp: "0\<le> x" and x1: "x < 1" 
  3894   shows "\<forall> a n s. Inum (x#bs) a = Inum (x#bs) (CN 0 n s) \<and> numbound0 s \<longrightarrow> Ifm (x#bs) (NDVD i n s) = Ifm (x#bs) (NDvd i a)"
  3895   (is "\<forall> a n s. ?N a = ?N (CN 0 n s) \<and> _ \<longrightarrow> ?I (NDVD i n s) = ?I (NDvd i a)")
  3896 proof(clarify)
  3897   fix a n s 
  3898   assume H: "?N a = ?N (CN 0 n s)" and nb: "numbound0 s"
  3899   let ?th = "?I (NDVD i n s) = ?I (NDvd i a)"
  3900   have "i=0 \<or> (i\<noteq>0 \<and> n=0) \<or> (i\<noteq>0 \<and> n < 0) \<or> (i\<noteq>0 \<and> n > 0)" by arith
  3901   moreover {assume iz: "i=0" hence ?th using neq_mono[rule_format, OF conjI[OF H nb]] 
  3902       by (simp add: NDVD_def rdvd_left_0_eq)}
  3903   moreover {assume inz: "i\<noteq>0" and "n=0" hence ?th by (simp add: H NDVD_def) } 
  3904   moreover {assume inz: "i\<noteq>0" and "n<0" hence ?th 
  3905       by (simp add: NDVD_def H NDVDJ_NDVD[OF xp x1] rdvd_abs1 
  3906         rdvd_minus[where d="i" and t="real n * x + Inum (x # bs) s"]) } 
  3907   moreover {assume inz: "i\<noteq>0" and "n>0" hence ?th 
  3908       by (simp add:NDVD_def H NDVDJ_NDVD[OF xp x1] rdvd_abs1)}
  3909   ultimately show ?th by blast
  3910 qed
  3911 
  3912 lemma DVD_l: "isrlfm (rsplit (DVD i) a)"
  3913   by (rule rsplit_l[where f="DVD i" and a="a"], auto simp add: DVD_def eq_def DVDJ_l) 
  3914 (case_tac s, simp_all, case_tac "nat", simp_all)
  3915 
  3916 lemma NDVD_l: "isrlfm (rsplit (NDVD i) a)"
  3917   by (rule rsplit_l[where f="NDVD i" and a="a"], auto simp add: NDVD_def neq_def NDVDJ_l) 
  3918 (case_tac s, simp_all, case_tac "nat", simp_all)
  3919 
  3920 consts rlfm :: "fm \<Rightarrow> fm"
  3921 recdef rlfm "measure fmsize"
  3922   "rlfm (And p q) = conj (rlfm p) (rlfm q)"
  3923   "rlfm (Or p q) = disj (rlfm p) (rlfm q)"
  3924   "rlfm (Imp p q) = disj (rlfm (NOT p)) (rlfm q)"
  3925   "rlfm (Iff p q) = disj (conj(rlfm p) (rlfm q)) (conj(rlfm (NOT p)) (rlfm (NOT q)))"
  3926   "rlfm (Lt a) = rsplit lt a"
  3927   "rlfm (Le a) = rsplit le a"
  3928   "rlfm (Gt a) = rsplit gt a"
  3929   "rlfm (Ge a) = rsplit ge a"
  3930   "rlfm (Eq a) = rsplit eq a"
  3931   "rlfm (NEq a) = rsplit neq a"
  3932   "rlfm (Dvd i a) = rsplit (\<lambda> t. DVD i t) a"
  3933   "rlfm (NDvd i a) = rsplit (\<lambda> t. NDVD i t) a"
  3934   "rlfm (NOT (And p q)) = disj (rlfm (NOT p)) (rlfm (NOT q))"
  3935   "rlfm (NOT (Or p q)) = conj (rlfm (NOT p)) (rlfm (NOT q))"
  3936   "rlfm (NOT (Imp p q)) = conj (rlfm p) (rlfm (NOT q))"
  3937   "rlfm (NOT (Iff p q)) = disj (conj(rlfm p) (rlfm(NOT q))) (conj(rlfm(NOT p)) (rlfm q))"
  3938   "rlfm (NOT (NOT p)) = rlfm p"
  3939   "rlfm (NOT T) = F"
  3940   "rlfm (NOT F) = T"
  3941   "rlfm (NOT (Lt a)) = simpfm (rlfm (Ge a))"
  3942   "rlfm (NOT (Le a)) = simpfm (rlfm (Gt a))"
  3943   "rlfm (NOT (Gt a)) = simpfm (rlfm (Le a))"
  3944   "rlfm (NOT (Ge a)) = simpfm (rlfm (Lt a))"
  3945   "rlfm (NOT (Eq a)) = simpfm (rlfm (NEq a))"
  3946   "rlfm (NOT (NEq a)) = simpfm (rlfm (Eq a))"
  3947   "rlfm (NOT (Dvd i a)) = simpfm (rlfm (NDvd i a))"
  3948   "rlfm (NOT (NDvd i a)) = simpfm (rlfm (Dvd i a))"
  3949   "rlfm p = p" (hints simp add: fmsize_pos)
  3950 
  3951 lemma bound0at_l : "\<lbrakk>isatom p ; bound0 p\<rbrakk> \<Longrightarrow> isrlfm p"
  3952   by (induct p rule: isrlfm.induct, auto)
  3953 
  3954 lemma simpfm_rl: "isrlfm p \<Longrightarrow> isrlfm (simpfm p)"
  3955 proof (induct p)
  3956   case (Lt a) 
  3957   hence "bound0 (Lt a) \<or> (\<exists> c e. a = CN 0 c e \<and> c > 0 \<and> numbound0 e)"
  3958     by (cases a,simp_all, case_tac "nat", simp_all)
  3959   moreover
  3960   {assume "bound0 (Lt a)" hence bn:"bound0 (simpfm (Lt a))"  
  3961       using simpfm_bound0 by blast
  3962     have "isatom (simpfm (Lt a))" by (cases "simpnum a", auto simp add: Let_def)
  3963     with bn bound0at_l have ?case by blast}
  3964   moreover 
  3965   { fix c e assume a: "a = CN 0 c e" and "c>0" and "numbound0 e"
  3966     { assume cn1:"numgcd (CN 0 c (simpnum e)) \<noteq> 1" and cnz:"numgcd (CN 0 c (simpnum e)) \<noteq> 0"
  3967       with numgcd_pos[where t="CN 0 c (simpnum e)"]
  3968       have th1:"numgcd (CN 0 c (simpnum e)) > 0" by simp
  3969       from `c > 0` have th:"numgcd (CN 0 c (simpnum e)) \<le> c" 
  3970         by (simp add: numgcd_def)
  3971       from `c > 0` have th': "c\<noteq>0" by auto
  3972       from `c > 0` have cp: "c \<ge> 0" by simp
  3973       from zdiv_mono2[OF cp th1 th, simplified div_self[OF th']]
  3974       have "0 < c div numgcd (CN 0 c (simpnum e))" by simp
  3975     }
  3976     with Lt a have ?case
  3977       by (simp add: Let_def reducecoeff_def reducecoeffh_numbound0)}
  3978   ultimately show ?case by blast
  3979 next
  3980   case (Le a)   
  3981   hence "bound0 (Le a) \<or> (\<exists> c e. a = CN 0 c e \<and> c > 0 \<and> numbound0 e)"
  3982     by (cases a,simp_all, case_tac "nat", simp_all)
  3983   moreover
  3984   { assume "bound0 (Le a)" hence bn:"bound0 (simpfm (Le a))"  
  3985       using simpfm_bound0 by blast
  3986     have "isatom (simpfm (Le a))" by (cases "simpnum a", auto simp add: Let_def)
  3987     with bn bound0at_l have ?case by blast}
  3988   moreover 
  3989   { fix c e assume a: "a = CN 0 c e" and "c>0" and "numbound0 e"
  3990     { assume cn1:"numgcd (CN 0 c (simpnum e)) \<noteq> 1" and cnz:"numgcd (CN 0 c (simpnum e)) \<noteq> 0"
  3991       with numgcd_pos[where t="CN 0 c (simpnum e)"]
  3992       have th1:"numgcd (CN 0 c (simpnum e)) > 0" by simp
  3993       from `c > 0` have th:"numgcd (CN 0 c (simpnum e)) \<le> c" 
  3994         by (simp add: numgcd_def)
  3995       from `c > 0` have th': "c\<noteq>0" by auto
  3996       from `c > 0` have cp: "c \<ge> 0" by simp
  3997       from zdiv_mono2[OF cp th1 th, simplified div_self[OF th']]
  3998       have "0 < c div numgcd (CN 0 c (simpnum e))" by simp
  3999     }
  4000     with Le a have ?case
  4001       by (simp add: Let_def reducecoeff_def simpnum_numbound0 reducecoeffh_numbound0)}
  4002   ultimately show ?case by blast
  4003 next
  4004   case (Gt a)   
  4005   hence "bound0 (Gt a) \<or> (\<exists> c e. a = CN 0 c e \<and> c > 0 \<and> numbound0 e)"
  4006     by (cases a,simp_all, case_tac "nat", simp_all)
  4007   moreover
  4008   {assume "bound0 (Gt a)" hence bn:"bound0 (simpfm (Gt a))"  
  4009       using simpfm_bound0 by blast
  4010     have "isatom (simpfm (Gt a))" by (cases "simpnum a", auto simp add: Let_def)
  4011     with bn bound0at_l have ?case by blast}
  4012   moreover 
  4013   { fix c e assume a: "a = CN 0 c e" and "c>0" and "numbound0 e"
  4014     { assume cn1: "numgcd (CN 0 c (simpnum e)) \<noteq> 1" and cnz:"numgcd (CN 0 c (simpnum e)) \<noteq> 0"
  4015       with numgcd_pos[where t="CN 0 c (simpnum e)"]
  4016       have th1:"numgcd (CN 0 c (simpnum e)) > 0" by simp
  4017       from `c > 0` have th:"numgcd (CN 0 c (simpnum e)) \<le> c" 
  4018         by (simp add: numgcd_def)
  4019       from `c > 0` have th': "c\<noteq>0" by auto
  4020       from `c > 0` have cp: "c \<ge> 0" by simp
  4021       from zdiv_mono2[OF cp th1 th, simplified div_self[OF th']]
  4022       have "0 < c div numgcd (CN 0 c (simpnum e))" by simp
  4023     }
  4024     with Gt a have ?case
  4025       by (simp add: Let_def reducecoeff_def simpnum_numbound0 reducecoeffh_numbound0)}
  4026   ultimately show ?case by blast
  4027 next
  4028   case (Ge a)   
  4029   hence "bound0 (Ge a) \<or> (\<exists> c e. a = CN 0 c e \<and> c > 0 \<and> numbound0 e)"
  4030     by (cases a,simp_all, case_tac "nat", simp_all)
  4031   moreover
  4032   { assume "bound0 (Ge a)" hence bn:"bound0 (simpfm (Ge a))"  
  4033       using simpfm_bound0 by blast
  4034     have "isatom (simpfm (Ge a))" by (cases "simpnum a", auto simp add: Let_def)
  4035     with bn bound0at_l have ?case by blast}
  4036   moreover 
  4037   { fix c e assume a: "a = CN 0 c e" and "c>0" and "numbound0 e"
  4038     { assume cn1:"numgcd (CN 0 c (simpnum e)) \<noteq> 1" and cnz:"numgcd (CN 0 c (simpnum e)) \<noteq> 0"
  4039       with numgcd_pos[where t="CN 0 c (simpnum e)"]
  4040       have th1:"numgcd (CN 0 c (simpnum e)) > 0" by simp
  4041       from `c > 0` have th:"numgcd (CN 0 c (simpnum e)) \<le> c" 
  4042         by (simp add: numgcd_def)
  4043       from `c > 0` have th': "c\<noteq>0" by auto
  4044       from `c > 0` have cp: "c \<ge> 0" by simp
  4045       from zdiv_mono2[OF cp th1 th, simplified div_self[OF th']]
  4046       have "0 < c div numgcd (CN 0 c (simpnum e))" by simp
  4047     }
  4048     with Ge a have ?case
  4049       by (simp add: Let_def reducecoeff_def simpnum_numbound0 reducecoeffh_numbound0)}
  4050   ultimately show ?case by blast
  4051 next
  4052   case (Eq a)   
  4053   hence "bound0 (Eq a) \<or> (\<exists> c e. a = CN 0 c e \<and> c > 0 \<and> numbound0 e)"
  4054     by (cases a,simp_all, case_tac "nat", simp_all)
  4055   moreover
  4056   { assume "bound0 (Eq a)" hence bn:"bound0 (simpfm (Eq a))"  
  4057       using simpfm_bound0 by blast
  4058     have "isatom (simpfm (Eq a))" by (cases "simpnum a", auto simp add: Let_def)
  4059     with bn bound0at_l have ?case by blast}
  4060   moreover 
  4061   { fix c e assume a: "a = CN 0 c e" and "c>0" and "numbound0 e"
  4062     { assume cn1:"numgcd (CN 0 c (simpnum e)) \<noteq> 1" and cnz:"numgcd (CN 0 c (simpnum e)) \<noteq> 0"
  4063       with numgcd_pos[where t="CN 0 c (simpnum e)"]
  4064       have th1:"numgcd (CN 0 c (simpnum e)) > 0" by simp
  4065       from `c > 0` have th:"numgcd (CN 0 c (simpnum e)) \<le> c" 
  4066         by (simp add: numgcd_def)
  4067       from `c > 0` have th': "c\<noteq>0" by auto
  4068       from `c > 0` have cp: "c \<ge> 0" by simp
  4069       from zdiv_mono2[OF cp th1 th, simplified div_self[OF th']]
  4070       have "0 < c div numgcd (CN 0 c (simpnum e))" by simp
  4071     }
  4072     with Eq a have ?case
  4073       by (simp add: Let_def reducecoeff_def simpnum_numbound0 reducecoeffh_numbound0)}
  4074   ultimately show ?case by blast
  4075 next
  4076   case (NEq a)  
  4077   hence "bound0 (NEq a) \<or> (\<exists> c e. a = CN 0 c e \<and> c > 0 \<and> numbound0 e)"
  4078     by (cases a,simp_all, case_tac "nat", simp_all)
  4079   moreover
  4080   {assume "bound0 (NEq a)" hence bn:"bound0 (simpfm (NEq a))"  
  4081       using simpfm_bound0 by blast
  4082     have "isatom (simpfm (NEq a))" by (cases "simpnum a", auto simp add: Let_def)
  4083     with bn bound0at_l have ?case by blast}
  4084   moreover 
  4085   { fix c e assume a: "a = CN 0 c e" and "c>0" and "numbound0 e"
  4086     { assume cn1:"numgcd (CN 0 c (simpnum e)) \<noteq> 1" and cnz:"numgcd (CN 0 c (simpnum e)) \<noteq> 0"
  4087       with numgcd_pos[where t="CN 0 c (simpnum e)"]
  4088       have th1:"numgcd (CN 0 c (simpnum e)) > 0" by simp
  4089       from `c > 0` have th:"numgcd (CN 0 c (simpnum e)) \<le> c" 
  4090         by (simp add: numgcd_def)
  4091       from `c > 0` have th': "c\<noteq>0" by auto
  4092       from `c > 0` have cp: "c \<ge> 0" by simp
  4093       from zdiv_mono2[OF cp th1 th, simplified div_self[OF th']]
  4094       have "0 < c div numgcd (CN 0 c (simpnum e))" by simp
  4095     }
  4096     with NEq a have ?case
  4097       by (simp add: Let_def reducecoeff_def simpnum_numbound0 reducecoeffh_numbound0)}
  4098   ultimately show ?case by blast
  4099 next
  4100   case (Dvd i a) hence "bound0 (Dvd i a)" by auto hence bn:"bound0 (simpfm (Dvd i a))"  
  4101     using simpfm_bound0 by blast
  4102   have "isatom (simpfm (Dvd i a))" by (cases "simpnum a", auto simp add: Let_def split_def)
  4103   with bn bound0at_l show ?case by blast
  4104 next
  4105   case (NDvd i a)  hence "bound0 (NDvd i a)" by auto hence bn:"bound0 (simpfm (NDvd i a))"  
  4106     using simpfm_bound0 by blast
  4107   have "isatom (simpfm (NDvd i a))" by (cases "simpnum a", auto simp add: Let_def split_def)
  4108   with bn bound0at_l show ?case by blast
  4109 qed(auto simp add: conj_def imp_def disj_def iff_def Let_def simpfm_bound0 numadd_nb numneg_nb)
  4110 
  4111 lemma rlfm_I:
  4112   assumes qfp: "qfree p"
  4113   and xp: "0 \<le> x" and x1: "x < 1"
  4114   shows "(Ifm (x#bs) (rlfm p) = Ifm (x# bs) p) \<and> isrlfm (rlfm p)"
  4115   using qfp 
  4116 by (induct p rule: rlfm.induct) 
  4117 (auto simp add: rsplit[OF xp x1 lt_mono] lt_l rsplit[OF xp x1 le_mono] le_l rsplit[OF xp x1 gt_mono] gt_l
  4118                rsplit[OF xp x1 ge_mono] ge_l rsplit[OF xp x1 eq_mono] eq_l rsplit[OF xp x1 neq_mono] neq_l
  4119                rsplit[OF xp x1 DVD_mono[OF xp x1]] DVD_l rsplit[OF xp x1 NDVD_mono[OF xp x1]] NDVD_l simpfm_rl)
  4120 lemma rlfm_l:
  4121   assumes qfp: "qfree p"
  4122   shows "isrlfm (rlfm p)"
  4123   using qfp lt_l gt_l ge_l le_l eq_l neq_l DVD_l NDVD_l 
  4124 by (induct p rule: rlfm.induct,auto simp add: simpfm_rl)
  4125 
  4126     (* Operations needed for Ferrante and Rackoff *)
  4127 lemma rminusinf_inf:
  4128   assumes lp: "isrlfm p"
  4129   shows "\<exists> z. \<forall> x < z. Ifm (x#bs) (minusinf p) = Ifm (x#bs) p" (is "\<exists> z. \<forall> x. ?P z x p")
  4130 using lp
  4131 proof (induct p rule: minusinf.induct)
  4132   case (1 p q) thus ?case by (auto,rule_tac x= "min z za" in exI) auto
  4133 next
  4134   case (2 p q) thus ?case by (auto,rule_tac x= "min z za" in exI) auto
  4135 next
  4136   case (3 c e) 
  4137   from 3 have nb: "numbound0 e" by simp
  4138   from 3 have cp: "real c > 0" by simp
  4139   fix a
  4140   let ?e="Inum (a#bs) e"
  4141   let ?z = "(- ?e) / real c"
  4142   {fix x
  4143     assume xz: "x < ?z"
  4144     hence "(real c * x < - ?e)" 
  4145       by (simp only: pos_less_divide_eq[OF cp, where a="x" and b="- ?e"] mult_ac) 
  4146     hence "real c * x + ?e < 0" by arith
  4147     hence "real c * x + ?e \<noteq> 0" by simp
  4148     with xz have "?P ?z x (Eq (CN 0 c e))"
  4149       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"] by simp  }
  4150   hence "\<forall> x < ?z. ?P ?z x (Eq (CN 0 c e))" by simp
  4151   thus ?case by blast
  4152 next
  4153   case (4 c e)   
  4154   from 4 have nb: "numbound0 e" by simp
  4155   from 4 have cp: "real c > 0" by simp
  4156   fix a
  4157   let ?e="Inum (a#bs) e"
  4158   let ?z = "(- ?e) / real c"
  4159   {fix x
  4160     assume xz: "x < ?z"
  4161     hence "(real c * x < - ?e)" 
  4162       by (simp only: pos_less_divide_eq[OF cp, where a="x" and b="- ?e"] mult_ac) 
  4163     hence "real c * x + ?e < 0" by arith
  4164     hence "real c * x + ?e \<noteq> 0" by simp
  4165     with xz have "?P ?z x (NEq (CN 0 c e))"
  4166       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"] by simp }
  4167   hence "\<forall> x < ?z. ?P ?z x (NEq (CN 0 c e))" by simp
  4168   thus ?case by blast
  4169 next
  4170   case (5 c e) 
  4171   from 5 have nb: "numbound0 e" by simp
  4172   from 5 have cp: "real c > 0" by simp
  4173   fix a
  4174   let ?e="Inum (a#bs) e"
  4175   let ?z = "(- ?e) / real c"
  4176   {fix x
  4177     assume xz: "x < ?z"
  4178     hence "(real c * x < - ?e)" 
  4179       by (simp only: pos_less_divide_eq[OF cp, where a="x" and b="- ?e"] mult_ac) 
  4180     hence "real c * x + ?e < 0" by arith
  4181     with xz have "?P ?z x (Lt (CN 0 c e))"
  4182       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"]  by simp }
  4183   hence "\<forall> x < ?z. ?P ?z x (Lt (CN 0 c e))" by simp
  4184   thus ?case by blast
  4185 next
  4186   case (6 c e)  
  4187   from 6 have nb: "numbound0 e" by simp
  4188   from 6 have cp: "real c > 0" by simp
  4189   fix a
  4190   let ?e="Inum (a#bs) e"
  4191   let ?z = "(- ?e) / real c"
  4192   {fix x
  4193     assume xz: "x < ?z"
  4194     hence "(real c * x < - ?e)" 
  4195       by (simp only: pos_less_divide_eq[OF cp, where a="x" and b="- ?e"] mult_ac) 
  4196     hence "real c * x + ?e < 0" by arith
  4197     with xz have "?P ?z x (Le (CN 0 c e))"
  4198       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"] by simp }
  4199   hence "\<forall> x < ?z. ?P ?z x (Le (CN 0 c e))" by simp
  4200   thus ?case by blast
  4201 next
  4202   case (7 c e)  
  4203   from 7 have nb: "numbound0 e" by simp
  4204   from 7 have cp: "real c > 0" by simp
  4205   fix a
  4206   let ?e="Inum (a#bs) e"
  4207   let ?z = "(- ?e) / real c"
  4208   {fix x
  4209     assume xz: "x < ?z"
  4210     hence "(real c * x < - ?e)" 
  4211       by (simp only: pos_less_divide_eq[OF cp, where a="x" and b="- ?e"] mult_ac) 
  4212     hence "real c * x + ?e < 0" by arith
  4213     with xz have "?P ?z x (Gt (CN 0 c e))"
  4214       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"] by simp }
  4215   hence "\<forall> x < ?z. ?P ?z x (Gt (CN 0 c e))" by simp
  4216   thus ?case by blast
  4217 next
  4218   case (8 c e)  
  4219   from 8 have nb: "numbound0 e" by simp
  4220   from 8 have cp: "real c > 0" by simp
  4221   fix a
  4222   let ?e="Inum (a#bs) e"
  4223   let ?z = "(- ?e) / real c"
  4224   {fix x
  4225     assume xz: "x < ?z"
  4226     hence "(real c * x < - ?e)" 
  4227       by (simp only: pos_less_divide_eq[OF cp, where a="x" and b="- ?e"] mult_ac) 
  4228     hence "real c * x + ?e < 0" by arith
  4229     with xz have "?P ?z x (Ge (CN 0 c e))"
  4230       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"] by simp }
  4231   hence "\<forall> x < ?z. ?P ?z x (Ge (CN 0 c e))" by simp
  4232   thus ?case by blast
  4233 qed simp_all
  4234 
  4235 lemma rplusinf_inf:
  4236   assumes lp: "isrlfm p"
  4237   shows "\<exists> z. \<forall> x > z. Ifm (x#bs) (plusinf p) = Ifm (x#bs) p" (is "\<exists> z. \<forall> x. ?P z x p")
  4238 using lp
  4239 proof (induct p rule: isrlfm.induct)
  4240   case (1 p q) thus ?case by (auto,rule_tac x= "max z za" in exI) auto
  4241 next
  4242   case (2 p q) thus ?case by (auto,rule_tac x= "max z za" in exI) auto
  4243 next
  4244   case (3 c e) 
  4245   from 3 have nb: "numbound0 e" by simp
  4246   from 3 have cp: "real c > 0" by simp
  4247   fix a
  4248   let ?e="Inum (a#bs) e"
  4249   let ?z = "(- ?e) / real c"
  4250   {fix x
  4251     assume xz: "x > ?z"
  4252     with mult_strict_right_mono [OF xz cp] cp
  4253     have "(real c * x > - ?e)" by (simp add: mult_ac)
  4254     hence "real c * x + ?e > 0" by arith
  4255     hence "real c * x + ?e \<noteq> 0" by simp
  4256     with xz have "?P ?z x (Eq (CN 0 c e))"
  4257       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"] by simp }
  4258   hence "\<forall> x > ?z. ?P ?z x (Eq (CN 0 c e))" by simp
  4259   thus ?case by blast
  4260 next
  4261   case (4 c e) 
  4262   from 4 have nb: "numbound0 e" by simp
  4263   from 4 have cp: "real c > 0" by simp
  4264   fix a
  4265   let ?e="Inum (a#bs) e"
  4266   let ?z = "(- ?e) / real c"
  4267   {fix x
  4268     assume xz: "x > ?z"
  4269     with mult_strict_right_mono [OF xz cp] cp
  4270     have "(real c * x > - ?e)" by (simp add: mult_ac)
  4271     hence "real c * x + ?e > 0" by arith
  4272     hence "real c * x + ?e \<noteq> 0" by simp
  4273     with xz have "?P ?z x (NEq (CN 0 c e))"
  4274       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"] by simp }
  4275   hence "\<forall> x > ?z. ?P ?z x (NEq (CN 0 c e))" by simp
  4276   thus ?case by blast
  4277 next
  4278   case (5 c e) 
  4279   from 5 have nb: "numbound0 e" by simp
  4280   from 5 have cp: "real c > 0" by simp
  4281   fix a
  4282   let ?e="Inum (a#bs) e"
  4283   let ?z = "(- ?e) / real c"
  4284   {fix x
  4285     assume xz: "x > ?z"
  4286     with mult_strict_right_mono [OF xz cp] cp
  4287     have "(real c * x > - ?e)" by (simp add: mult_ac)
  4288     hence "real c * x + ?e > 0" by arith
  4289     with xz have "?P ?z x (Lt (CN 0 c e))"
  4290       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"] by simp }
  4291   hence "\<forall> x > ?z. ?P ?z x (Lt (CN 0 c e))" by simp
  4292   thus ?case by blast
  4293 next
  4294   case (6 c e) 
  4295   from 6 have nb: "numbound0 e" by simp
  4296   from 6 have cp: "real c > 0" by simp
  4297   fix a
  4298   let ?e="Inum (a#bs) e"
  4299   let ?z = "(- ?e) / real c"
  4300   {fix x
  4301     assume xz: "x > ?z"
  4302     with mult_strict_right_mono [OF xz cp] cp
  4303     have "(real c * x > - ?e)" by (simp add: mult_ac)
  4304     hence "real c * x + ?e > 0" by arith
  4305     with xz have "?P ?z x (Le (CN 0 c e))"
  4306       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"] by simp }
  4307   hence "\<forall> x > ?z. ?P ?z x (Le (CN 0 c e))" by simp
  4308   thus ?case by blast
  4309 next
  4310   case (7 c e) 
  4311   from 7 have nb: "numbound0 e" by simp
  4312   from 7 have cp: "real c > 0" by simp
  4313   fix a
  4314   let ?e="Inum (a#bs) e"
  4315   let ?z = "(- ?e) / real c"
  4316   {fix x
  4317     assume xz: "x > ?z"
  4318     with mult_strict_right_mono [OF xz cp] cp
  4319     have "(real c * x > - ?e)" by (simp add: mult_ac)
  4320     hence "real c * x + ?e > 0" by arith
  4321     with xz have "?P ?z x (Gt (CN 0 c e))"
  4322       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"] by simp }
  4323   hence "\<forall> x > ?z. ?P ?z x (Gt (CN 0 c e))" by simp
  4324   thus ?case by blast
  4325 next
  4326   case (8 c e) 
  4327   from 8 have nb: "numbound0 e" by simp
  4328   from 8 have cp: "real c > 0" by simp
  4329   fix a
  4330   let ?e="Inum (a#bs) e"
  4331   let ?z = "(- ?e) / real c"
  4332   {fix x
  4333     assume xz: "x > ?z"
  4334     with mult_strict_right_mono [OF xz cp] cp
  4335     have "(real c * x > - ?e)" by (simp add: mult_ac)
  4336     hence "real c * x + ?e > 0" by arith
  4337     with xz have "?P ?z x (Ge (CN 0 c e))"
  4338       using numbound0_I[OF nb, where b="x" and bs="bs" and b'="a"]   by simp }
  4339   hence "\<forall> x > ?z. ?P ?z x (Ge (CN 0 c e))" by simp
  4340   thus ?case by blast
  4341 qed simp_all
  4342 
  4343 lemma rminusinf_bound0:
  4344   assumes lp: "isrlfm p"
  4345   shows "bound0 (minusinf p)"
  4346   using lp
  4347   by (induct p rule: minusinf.induct) simp_all
  4348 
  4349 lemma rplusinf_bound0:
  4350   assumes lp: "isrlfm p"
  4351   shows "bound0 (plusinf p)"
  4352   using lp
  4353   by (induct p rule: plusinf.induct) simp_all
  4354 
  4355 lemma rminusinf_ex:
  4356   assumes lp: "isrlfm p"
  4357   and ex: "Ifm (a#bs) (minusinf p)"
  4358   shows "\<exists> x. Ifm (x#bs) p"
  4359 proof-
  4360   from bound0_I [OF rminusinf_bound0[OF lp], where b="a" and bs ="bs"] ex
  4361   have th: "\<forall> x. Ifm (x#bs) (minusinf p)" by auto
  4362   from rminusinf_inf[OF lp, where bs="bs"] 
  4363   obtain z where z_def: "\<forall>x<z. Ifm (x # bs) (minusinf p) = Ifm (x # bs) p" by blast
  4364   from th have "Ifm ((z - 1)#bs) (minusinf p)" by simp
  4365   moreover have "z - 1 < z" by simp
  4366   ultimately show ?thesis using z_def by auto
  4367 qed
  4368 
  4369 lemma rplusinf_ex:
  4370   assumes lp: "isrlfm p"
  4371   and ex: "Ifm (a#bs) (plusinf p)"
  4372   shows "\<exists> x. Ifm (x#bs) p"
  4373 proof-
  4374   from bound0_I [OF rplusinf_bound0[OF lp], where b="a" and bs ="bs"] ex
  4375   have th: "\<forall> x. Ifm (x#bs) (plusinf p)" by auto
  4376   from rplusinf_inf[OF lp, where bs="bs"] 
  4377   obtain z where z_def: "\<forall>x>z. Ifm (x # bs) (plusinf p) = Ifm (x # bs) p" by blast
  4378   from th have "Ifm ((z + 1)#bs) (plusinf p)" by simp
  4379   moreover have "z + 1 > z" by simp
  4380   ultimately show ?thesis using z_def by auto
  4381 qed
  4382 
  4383 consts 
  4384   \<Upsilon>:: "fm \<Rightarrow> (num \<times> int) list"
  4385   \<upsilon> :: "fm \<Rightarrow> (num \<times> int) \<Rightarrow> fm "
  4386 recdef \<Upsilon> "measure size"
  4387   "\<Upsilon> (And p q) = (\<Upsilon> p @ \<Upsilon> q)" 
  4388   "\<Upsilon> (Or p q) = (\<Upsilon> p @ \<Upsilon> q)" 
  4389   "\<Upsilon> (Eq  (CN 0 c e)) = [(Neg e,c)]"
  4390   "\<Upsilon> (NEq (CN 0 c e)) = [(Neg e,c)]"
  4391   "\<Upsilon> (Lt  (CN 0 c e)) = [(Neg e,c)]"
  4392   "\<Upsilon> (Le  (CN 0 c e)) = [(Neg e,c)]"
  4393   "\<Upsilon> (Gt  (CN 0 c e)) = [(Neg e,c)]"
  4394   "\<Upsilon> (Ge  (CN 0 c e)) = [(Neg e,c)]"
  4395   "\<Upsilon> p = []"
  4396 
  4397 recdef \<upsilon> "measure size"
  4398   "\<upsilon> (And p q) = (\<lambda> (t,n). And (\<upsilon> p (t,n)) (\<upsilon> q (t,n)))"
  4399   "\<upsilon> (Or p q) = (\<lambda> (t,n). Or (\<upsilon> p (t,n)) (\<upsilon> q (t,n)))"
  4400   "\<upsilon> (Eq (CN 0 c e)) = (\<lambda> (t,n). Eq (Add (Mul c t) (Mul n e)))"
  4401   "\<upsilon> (NEq (CN 0 c e)) = (\<lambda> (t,n). NEq (Add (Mul c t) (Mul n e)))"
  4402   "\<upsilon> (Lt (CN 0 c e)) = (\<lambda> (t,n). Lt (Add (Mul c t) (Mul n e)))"
  4403   "\<upsilon> (Le (CN 0 c e)) = (\<lambda> (t,n). Le (Add (Mul c t) (Mul n e)))"
  4404   "\<upsilon> (Gt (CN 0 c e)) = (\<lambda> (t,n). Gt (Add (Mul c t) (Mul n e)))"
  4405   "\<upsilon> (Ge (CN 0 c e)) = (\<lambda> (t,n). Ge (Add (Mul c t) (Mul n e)))"
  4406   "\<upsilon> p = (\<lambda> (t,n). p)"
  4407 
  4408 lemma \<upsilon>_I: assumes lp: "isrlfm p"
  4409   and np: "real n > 0" and nbt: "numbound0 t"
  4410   shows "(Ifm (x#bs) (\<upsilon> p (t,n)) = Ifm (((Inum (x#bs) t)/(real n))#bs) p) \<and> bound0 (\<upsilon> p (t,n))" (is "(?I x (\<upsilon> p (t,n)) = ?I ?u p) \<and> ?B p" is "(_ = ?I (?t/?n) p) \<and> _" is "(_ = ?I (?N x t /_) p) \<and> _")
  4411   using lp
  4412 proof(induct p rule: \<upsilon>.induct)
  4413   case (5 c e)
  4414   from 5 have cp: "c >0" and nb: "numbound0 e" by simp_all
  4415   have "?I ?u (Lt (CN 0 c e)) = (real c *(?t/?n) + (?N x e) < 0)"
  4416     using numbound0_I[OF nb, where bs="bs" and b="?u" and b'="x"] by simp
  4417   also have "\<dots> = (?n*(real c *(?t/?n)) + ?n*(?N x e) < 0)"
  4418     by (simp only: pos_less_divide_eq[OF np, where a="real c *(?t/?n) + (?N x e)" 
  4419       and b="0", simplified divide_zero_left]) (simp only: algebra_simps)
  4420   also have "\<dots> = (real c *?t + ?n* (?N x e) < 0)"
  4421     using np by simp 
  4422   finally show ?case using nbt nb by (simp add: algebra_simps)
  4423 next
  4424   case (6 c e)
  4425   from 6 have cp: "c >0" and nb: "numbound0 e" by simp_all
  4426   have "?I ?u (Le (CN 0 c e)) = (real c *(?t/?n) + (?N x e) \<le> 0)"
  4427     using numbound0_I[OF nb, where bs="bs" and b="?u" and b'="x"] by simp
  4428   also have "\<dots> = (?n*(real c *(?t/?n)) + ?n*(?N x e) \<le> 0)"
  4429     by (simp only: pos_le_divide_eq[OF np, where a="real c *(?t/?n) + (?N x e)" 
  4430       and b="0", simplified divide_zero_left]) (simp only: algebra_simps)
  4431   also have "\<dots> = (real c *?t + ?n* (?N x e) \<le> 0)"
  4432     using np by simp 
  4433   finally show ?case using nbt nb by (simp add: algebra_simps)
  4434 next
  4435   case (7 c e)
  4436   from 7 have cp: "c >0" and nb: "numbound0 e" by simp_all
  4437   have "?I ?u (Gt (CN 0 c e)) = (real c *(?t/?n) + (?N x e) > 0)"
  4438     using numbound0_I[OF nb, where bs="bs" and b="?u" and b'="x"] by simp
  4439   also have "\<dots> = (?n*(real c *(?t/?n)) + ?n*(?N x e) > 0)"
  4440     by (simp only: pos_divide_less_eq[OF np, where a="real c *(?t/?n) + (?N x e)" 
  4441       and b="0", simplified divide_zero_left]) (simp only: algebra_simps)
  4442   also have "\<dots> = (real c *?t + ?n* (?N x e) > 0)"
  4443     using np by simp 
  4444   finally show ?case using nbt nb by (simp add: algebra_simps)
  4445 next
  4446   case (8 c e)
  4447   from 8 have cp: "c >0" and nb: "numbound0 e" by simp_all
  4448   have "?I ?u (Ge (CN 0 c e)) = (real c *(?t/?n) + (?N x e) \<ge> 0)"
  4449     using numbound0_I[OF nb, where bs="bs" and b="?u" and b'="x"] by simp
  4450   also have "\<dots> = (?n*(real c *(?t/?n)) + ?n*(?N x e) \<ge> 0)"
  4451     by (simp only: pos_divide_le_eq[OF np, where a="real c *(?t/?n) + (?N x e)" 
  4452       and b="0", simplified divide_zero_left]) (simp only: algebra_simps)
  4453   also have "\<dots> = (real c *?t + ?n* (?N x e) \<ge> 0)"
  4454     using np by simp 
  4455   finally show ?case using nbt nb by (simp add: algebra_simps)
  4456 next
  4457   case (3 c e)
  4458   from 3 have cp: "c >0" and nb: "numbound0 e" by simp_all
  4459   from np have np: "real n \<noteq> 0" by simp
  4460   have "?I ?u (Eq (CN 0 c e)) = (real c *(?t/?n) + (?N x e) = 0)"
  4461     using numbound0_I[OF nb, where bs="bs" and b="?u" and b'="x"] by simp
  4462   also have "\<dots> = (?n*(real c *(?t/?n)) + ?n*(?N x e) = 0)"
  4463     by (simp only: nonzero_eq_divide_eq[OF np, where a="real c *(?t/?n) + (?N x e)" 
  4464       and b="0", simplified divide_zero_left]) (simp only: algebra_simps)
  4465   also have "\<dots> = (real c *?t + ?n* (?N x e) = 0)"
  4466     using np by simp 
  4467   finally show ?case using nbt nb by (simp add: algebra_simps)
  4468 next
  4469   case (4 c e)
  4470   from 4 have cp: "c >0" and nb: "numbound0 e" by simp_all
  4471   from np have np: "real n \<noteq> 0" by simp
  4472   have "?I ?u (NEq (CN 0 c e)) = (real c *(?t/?n) + (?N x e) \<noteq> 0)"
  4473     using numbound0_I[OF nb, where bs="bs" and b="?u" and b'="x"] by simp
  4474   also have "\<dots> = (?n*(real c *(?t/?n)) + ?n*(?N x e) \<noteq> 0)"
  4475     by (simp only: nonzero_eq_divide_eq[OF np, where a="real c *(?t/?n) + (?N x e)" 
  4476       and b="0", simplified divide_zero_left]) (simp only: algebra_simps)
  4477   also have "\<dots> = (real c *?t + ?n* (?N x e) \<noteq> 0)"
  4478     using np by simp 
  4479   finally show ?case using nbt nb by (simp add: algebra_simps)
  4480 qed(simp_all add: nbt numbound0_I[where bs ="bs" and b="(Inum (x#bs) t)/ real n" and b'="x"])
  4481 
  4482 lemma \<Upsilon>_l:
  4483   assumes lp: "isrlfm p"
  4484   shows "\<forall> (t,k) \<in> set (\<Upsilon> p). numbound0 t \<and> k >0"
  4485 using lp
  4486 by(induct p rule: \<Upsilon>.induct)  auto
  4487 
  4488 lemma rminusinf_\<Upsilon>:
  4489   assumes lp: "isrlfm p"
  4490   and nmi: "\<not> (Ifm (a#bs) (minusinf p))" (is "\<not> (Ifm (a#bs) (?M p))")
  4491   and ex: "Ifm (x#bs) p" (is "?I x p")
  4492   shows "\<exists> (s,m) \<in> set (\<Upsilon> p). x \<ge> Inum (a#bs) s / real m" (is "\<exists> (s,m) \<in> ?U p. x \<ge> ?N a s / real m")
  4493 proof-
  4494   have "\<exists> (s,m) \<in> set (\<Upsilon> p). real m * x \<ge> Inum (a#bs) s " (is "\<exists> (s,m) \<in> ?U p. real m *x \<ge> ?N a s")
  4495     using lp nmi ex
  4496     by (induct p rule: minusinf.induct, auto simp add:numbound0_I[where bs="bs" and b="a" and b'="x"])
  4497   then obtain s m where smU: "(s,m) \<in> set (\<Upsilon> p)" and mx: "real m * x \<ge> ?N a s" by blast
  4498   from \<Upsilon>_l[OF lp] smU have mp: "real m > 0" by auto
  4499   from pos_divide_le_eq[OF mp, where a="x" and b="?N a s", symmetric] mx have "x \<ge> ?N a s / real m" 
  4500     by (auto simp add: mult_commute)
  4501   thus ?thesis using smU by auto
  4502 qed
  4503 
  4504 lemma rplusinf_\<Upsilon>:
  4505   assumes lp: "isrlfm p"
  4506   and nmi: "\<not> (Ifm (a#bs) (plusinf p))" (is "\<not> (Ifm (a#bs) (?M p))")
  4507   and ex: "Ifm (x#bs) p" (is "?I x p")
  4508   shows "\<exists> (s,m) \<in> set (\<Upsilon> p). x \<le> Inum (a#bs) s / real m" (is "\<exists> (s,m) \<in> ?U p. x \<le> ?N a s / real m")
  4509 proof-
  4510   have "\<exists> (s,m) \<in> set (\<Upsilon> p). real m * x \<le> Inum (a#bs) s " (is "\<exists> (s,m) \<in> ?U p. real m *x \<le> ?N a s")
  4511     using lp nmi ex
  4512     by (induct p rule: minusinf.induct, auto simp add:numbound0_I[where bs="bs" and b="a" and b'="x"])
  4513   then obtain s m where smU: "(s,m) \<in> set (\<Upsilon> p)" and mx: "real m * x \<le> ?N a s" by blast
  4514   from \<Upsilon>_l[OF lp] smU have mp: "real m > 0" by auto
  4515   from pos_le_divide_eq[OF mp, where a="x" and b="?N a s", symmetric] mx have "x \<le> ?N a s / real m" 
  4516     by (auto simp add: mult_commute)
  4517   thus ?thesis using smU by auto
  4518 qed
  4519 
  4520 lemma lin_dense: 
  4521   assumes lp: "isrlfm p"
  4522   and noS: "\<forall> t. l < t \<and> t< u \<longrightarrow> t \<notin> (\<lambda> (t,n). Inum (x#bs) t / real n) ` set (\<Upsilon> p)" 
  4523   (is "\<forall> t. _ \<and> _ \<longrightarrow> t \<notin> (\<lambda> (t,n). ?N x t / real n ) ` (?U p)")
  4524   and lx: "l < x" and xu:"x < u" and px:" Ifm (x#bs) p"
  4525   and ly: "l < y" and yu: "y < u"
  4526   shows "Ifm (y#bs) p"
  4527 using lp px noS
  4528 proof (induct p rule: isrlfm.induct)
  4529   case (5 c e) hence cp: "real c > 0" and nb: "numbound0 e" by simp_all
  4530   from 5 have "x * real c + ?N x e < 0" by (simp add: algebra_simps)
  4531   hence pxc: "x < (- ?N x e) / real c" 
  4532     by (simp only: pos_less_divide_eq[OF cp, where a="x" and b="-?N x e"])
  4533   from 5 have noSc:"\<forall> t. l < t \<and> t < u \<longrightarrow> t \<noteq> (- ?N x e) / real c" by auto
  4534   with ly yu have yne: "y \<noteq> - ?N x e / real c" by auto
  4535   hence "y < (- ?N x e) / real c \<or> y > (-?N x e) / real c" by auto
  4536   moreover {assume y: "y < (-?N x e)/ real c"
  4537     hence "y * real c < - ?N x e"
  4538       by (simp add: pos_less_divide_eq[OF cp, where a="y" and b="-?N x e", symmetric])
  4539     hence "real c * y + ?N x e < 0" by (simp add: algebra_simps)
  4540     hence ?case using numbound0_I[OF nb, where bs="bs" and b="x" and b'="y"] by simp}
  4541   moreover {assume y: "y > (- ?N x e) / real c" 
  4542     with yu have eu: "u > (- ?N x e) / real c" by auto
  4543     with noSc ly yu have "(- ?N x e) / real c \<le> l" by (cases "(- ?N x e) / real c > l", auto)
  4544     with lx pxc have "False" by auto
  4545     hence ?case by simp }
  4546   ultimately show ?case by blast
  4547 next
  4548   case (6 c e) hence cp: "real c > 0" and nb: "numbound0 e" by simp_all
  4549   from 6 have "x * real c + ?N x e \<le> 0" by (simp add: algebra_simps)
  4550   hence pxc: "x \<le> (- ?N x e) / real c" 
  4551     by (simp only: pos_le_divide_eq[OF cp, where a="x" and b="-?N x e"])
  4552   from 6 have noSc:"\<forall> t. l < t \<and> t < u \<longrightarrow> t \<noteq> (- ?N x e) / real c" by auto
  4553   with ly yu have yne: "y \<noteq> - ?N x e / real c" by auto
  4554   hence "y < (- ?N x e) / real c \<or> y > (-?N x e) / real c" by auto
  4555   moreover {assume y: "y < (-?N x e)/ real c"
  4556     hence "y * real c < - ?N x e"
  4557       by (simp add: pos_less_divide_eq[OF cp, where a="y" and b="-?N x e", symmetric])
  4558     hence "real c * y + ?N x e < 0" by (simp add: algebra_simps)
  4559     hence ?case using numbound0_I[OF nb, where bs="bs" and b="x" and b'="y"] by simp}
  4560   moreover {assume y: "y > (- ?N x e) / real c" 
  4561     with yu have eu: "u > (- ?N x e) / real c" by auto
  4562     with noSc ly yu have "(- ?N x e) / real c \<le> l" by (cases "(- ?N x e) / real c > l", auto)
  4563     with lx pxc have "False" by auto
  4564     hence ?case by simp }
  4565   ultimately show ?case by blast
  4566 next
  4567   case (7 c e) hence cp: "real c > 0" and nb: "numbound0 e" by simp_all
  4568   from 7 have "x * real c + ?N x e > 0" by (simp add: algebra_simps)
  4569   hence pxc: "x > (- ?N x e) / real c" 
  4570     by (simp only: pos_divide_less_eq[OF cp, where a="x" and b="-?N x e"])
  4571   from 7 have noSc:"\<forall> t. l < t \<and> t < u \<longrightarrow> t \<noteq> (- ?N x e) / real c" by auto
  4572   with ly yu have yne: "y \<noteq> - ?N x e / real c" by auto
  4573   hence "y < (- ?N x e) / real c \<or> y > (-?N x e) / real c" by auto
  4574   moreover {assume y: "y > (-?N x e)/ real c"
  4575     hence "y * real c > - ?N x e"
  4576       by (simp add: pos_divide_less_eq[OF cp, where a="y" and b="-?N x e", symmetric])
  4577     hence "real c * y + ?N x e > 0" by (simp add: algebra_simps)
  4578     hence ?case using numbound0_I[OF nb, where bs="bs" and b="x" and b'="y"] by simp}
  4579   moreover {assume y: "y < (- ?N x e) / real c" 
  4580     with ly have eu: "l < (- ?N x e) / real c" by auto
  4581     with noSc ly yu have "(- ?N x e) / real c \<ge> u" by (cases "(- ?N x e) / real c > l", auto)
  4582     with xu pxc have "False" by auto
  4583     hence ?case by simp }
  4584   ultimately show ?case by blast
  4585 next
  4586   case (8 c e) hence cp: "real c > 0" and nb: "numbound0 e" by simp_all
  4587   from 8 have "x * real c + ?N x e \<ge> 0" by (simp add: algebra_simps)
  4588   hence pxc: "x \<ge> (- ?N x e) / real c" 
  4589     by (simp only: pos_divide_le_eq[OF cp, where a="x" and b="-?N x e"])
  4590   from 8 have noSc:"\<forall> t. l < t \<and> t < u \<longrightarrow> t \<noteq> (- ?N x e) / real c" by auto
  4591   with ly yu have yne: "y \<noteq> - ?N x e / real c" by auto
  4592   hence "y < (- ?N x e) / real c \<or> y > (-?N x e) / real c" by auto
  4593   moreover {assume y: "y > (-?N x e)/ real c"
  4594     hence "y * real c > - ?N x e"
  4595       by (simp add: pos_divide_less_eq[OF cp, where a="y" and b="-?N x e", symmetric])
  4596     hence "real c * y + ?N x e > 0" by (simp add: algebra_simps)
  4597     hence ?case using numbound0_I[OF nb, where bs="bs" and b="x" and b'="y"] by simp}
  4598   moreover {assume y: "y < (- ?N x e) / real c" 
  4599     with ly have eu: "l < (- ?N x e) / real c" by auto
  4600     with noSc ly yu have "(- ?N x e) / real c \<ge> u" by (cases "(- ?N x e) / real c > l", auto)
  4601     with xu pxc have "False" by auto
  4602     hence ?case by simp }
  4603   ultimately show ?case by blast
  4604 next
  4605   case (3 c e) hence cp: "real c > 0" and nb: "numbound0 e" by simp_all
  4606   from cp have cnz: "real c \<noteq> 0" by simp
  4607   from 3 have "x * real c + ?N x e = 0" by (simp add: algebra_simps)
  4608   hence pxc: "x = (- ?N x e) / real c" 
  4609     by (simp only: nonzero_eq_divide_eq[OF cnz, where a="x" and b="-?N x e"])
  4610   from 3 have noSc:"\<forall> t. l < t \<and> t < u \<longrightarrow> t \<noteq> (- ?N x e) / real c" by auto
  4611   with lx xu have yne: "x \<noteq> - ?N x e / real c" by auto
  4612   with pxc show ?case by simp
  4613 next
  4614   case (4 c e) hence cp: "real c > 0" and nb: "numbound0 e" by simp_all
  4615   from cp have cnz: "real c \<noteq> 0" by simp
  4616   from 4 have noSc:"\<forall> t. l < t \<and> t < u \<longrightarrow> t \<noteq> (- ?N x e) / real c" by auto
  4617   with ly yu have yne: "y \<noteq> - ?N x e / real c" by auto
  4618   hence "y* real c \<noteq> -?N x e"      
  4619     by (simp only: nonzero_eq_divide_eq[OF cnz, where a="y" and b="-?N x e"]) simp
  4620   hence "y* real c + ?N x e \<noteq> 0" by (simp add: algebra_simps)
  4621   thus ?case using numbound0_I[OF nb, where bs="bs" and b="x" and b'="y"] 
  4622     by (simp add: algebra_simps)
  4623 qed (auto simp add: numbound0_I[where bs="bs" and b="y" and b'="x"])
  4624 
  4625 lemma rinf_\<Upsilon>:
  4626   assumes lp: "isrlfm p"
  4627   and nmi: "\<not> (Ifm (x#bs) (minusinf p))" (is "\<not> (Ifm (x#bs) (?M p))")
  4628   and npi: "\<not> (Ifm (x#bs) (plusinf p))" (is "\<not> (Ifm (x#bs) (?P p))")
  4629   and ex: "\<exists> x.  Ifm (x#bs) p" (is "\<exists> x. ?I x p")
  4630   shows "\<exists> (l,n) \<in> set (\<Upsilon> p). \<exists> (s,m) \<in> set (\<Upsilon> p).
  4631     ?I ((Inum (x#bs) l / real n + Inum (x#bs) s / real m) / 2) p" 
  4632 proof-
  4633   let ?N = "\<lambda> x t. Inum (x#bs) t"
  4634   let ?U = "set (\<Upsilon> p)"
  4635   from ex obtain a where pa: "?I a p" by blast
  4636   from bound0_I[OF rminusinf_bound0[OF lp], where bs="bs" and b="x" and b'="a"] nmi
  4637   have nmi': "\<not> (?I a (?M p))" by simp
  4638   from bound0_I[OF rplusinf_bound0[OF lp], where bs="bs" and b="x" and b'="a"] npi
  4639   have npi': "\<not> (?I a (?P p))" by simp
  4640   have "\<exists> (l,n) \<in> set (\<Upsilon> p). \<exists> (s,m) \<in> set (\<Upsilon> p). ?I ((?N a l/real n + ?N a s /real m) / 2) p"
  4641   proof-
  4642     let ?M = "(\<lambda> (t,c). ?N a t / real c) ` ?U"
  4643     have fM: "finite ?M" by auto
  4644     from rminusinf_\<Upsilon>[OF lp nmi pa] rplusinf_\<Upsilon>[OF lp npi pa] 
  4645     have "\<exists> (l,n) \<in> set (\<Upsilon> p). \<exists> (s,m) \<in> set (\<Upsilon> p). a \<le> ?N x l / real n \<and> a \<ge> ?N x s / real m" by blast
  4646     then obtain "t" "n" "s" "m" where 
  4647       tnU: "(t,n) \<in> ?U" and smU: "(s,m) \<in> ?U" 
  4648       and xs1: "a \<le> ?N x s / real m" and tx1: "a \<ge> ?N x t / real n" by blast
  4649     from \<Upsilon>_l[OF lp] tnU smU numbound0_I[where bs="bs" and b="x" and b'="a"] xs1 tx1 have xs: "a \<le> ?N a s / real m" and tx: "a \<ge> ?N a t / real n" by auto
  4650     from tnU have Mne: "?M \<noteq> {}" by auto
  4651     hence Une: "?U \<noteq> {}" by simp
  4652     let ?l = "Min ?M"
  4653     let ?u = "Max ?M"
  4654     have linM: "?l \<in> ?M" using fM Mne by simp
  4655     have uinM: "?u \<in> ?M" using fM Mne by simp
  4656     have tnM: "?N a t / real n \<in> ?M" using tnU by auto
  4657     have smM: "?N a s / real m \<in> ?M" using smU by auto 
  4658     have lM: "\<forall> t\<in> ?M. ?l \<le> t" using Mne fM by auto
  4659     have Mu: "\<forall> t\<in> ?M. t \<le> ?u" using Mne fM by auto
  4660     have "?l \<le> ?N a t / real n" using tnM Mne by simp hence lx: "?l \<le> a" using tx by simp
  4661     have "?N a s / real m \<le> ?u" using smM Mne by simp hence xu: "a \<le> ?u" using xs by simp
  4662     from finite_set_intervals2[where P="\<lambda> x. ?I x p",OF pa lx xu linM uinM fM lM Mu]
  4663     have "(\<exists> s\<in> ?M. ?I s p) \<or> 
  4664       (\<exists> t1\<in> ?M. \<exists> t2 \<in> ?M. (\<forall> y. t1 < y \<and> y < t2 \<longrightarrow> y \<notin> ?M) \<and> t1 < a \<and> a < t2 \<and> ?I a p)" .
  4665     moreover { fix u assume um: "u\<in> ?M" and pu: "?I u p"
  4666       hence "\<exists> (tu,nu) \<in> ?U. u = ?N a tu / real nu" by auto
  4667       then obtain "tu" "nu" where tuU: "(tu,nu) \<in> ?U" and tuu:"u= ?N a tu / real nu" by blast
  4668       have "(u + u) / 2 = u" by auto with pu tuu 
  4669       have "?I (((?N a tu / real nu) + (?N a tu / real nu)) / 2) p" by simp
  4670       with tuU have ?thesis by blast}
  4671     moreover{
  4672       assume "\<exists> t1\<in> ?M. \<exists> t2 \<in> ?M. (\<forall> y. t1 < y \<and> y < t2 \<longrightarrow> y \<notin> ?M) \<and> t1 < a \<and> a < t2 \<and> ?I a p"
  4673       then obtain t1 and t2 where t1M: "t1 \<in> ?M" and t2M: "t2\<in> ?M" 
  4674         and noM: "\<forall> y. t1 < y \<and> y < t2 \<longrightarrow> y \<notin> ?M" and t1x: "t1 < a" and xt2: "a < t2" and px: "?I a p"
  4675         by blast
  4676       from t1M have "\<exists> (t1u,t1n) \<in> ?U. t1 = ?N a t1u / real t1n" by auto
  4677       then obtain "t1u" "t1n" where t1uU: "(t1u,t1n) \<in> ?U" and t1u: "t1 = ?N a t1u / real t1n" by blast
  4678       from t2M have "\<exists> (t2u,t2n) \<in> ?U. t2 = ?N a t2u / real t2n" by auto
  4679       then obtain "t2u" "t2n" where t2uU: "(t2u,t2n) \<in> ?U" and t2u: "t2 = ?N a t2u / real t2n" by blast
  4680       from t1x xt2 have t1t2: "t1 < t2" by simp
  4681       let ?u = "(t1 + t2) / 2"
  4682       from less_half_sum[OF t1t2] gt_half_sum[OF t1t2] have t1lu: "t1 < ?u" and ut2: "?u < t2" by auto
  4683       from lin_dense[OF lp noM t1x xt2 px t1lu ut2] have "?I ?u p" .
  4684       with t1uU t2uU t1u t2u have ?thesis by blast}
  4685     ultimately show ?thesis by blast
  4686   qed
  4687   then obtain "l" "n" "s"  "m" where lnU: "(l,n) \<in> ?U" and smU:"(s,m) \<in> ?U" 
  4688     and pu: "?I ((?N a l / real n + ?N a s / real m) / 2) p" by blast
  4689   from lnU smU \<Upsilon>_l[OF lp] have nbl: "numbound0 l" and nbs: "numbound0 s" by auto
  4690   from numbound0_I[OF nbl, where bs="bs" and b="a" and b'="x"] 
  4691     numbound0_I[OF nbs, where bs="bs" and b="a" and b'="x"] pu
  4692   have "?I ((?N x l / real n + ?N x s / real m) / 2) p" by simp
  4693   with lnU smU
  4694   show ?thesis by auto
  4695 qed
  4696     (* The Ferrante - Rackoff Theorem *)
  4697 
  4698 theorem fr_eq: 
  4699   assumes lp: "isrlfm p"
  4700   shows "(\<exists> x. Ifm (x#bs) p) = ((Ifm (x#bs) (minusinf p)) \<or> (Ifm (x#bs) (plusinf p)) \<or> (\<exists> (t,n) \<in> set (\<Upsilon> p). \<exists> (s,m) \<in> set (\<Upsilon> p). Ifm ((((Inum (x#bs) t)/  real n + (Inum (x#bs) s) / real m) /2)#bs) p))"
  4701   (is "(\<exists> x. ?I x p) = (?M \<or> ?P \<or> ?F)" is "?E = ?D")
  4702 proof
  4703   assume px: "\<exists> x. ?I x p"
  4704   have "?M \<or> ?P \<or> (\<not> ?M \<and> \<not> ?P)" by blast
  4705   moreover {assume "?M \<or> ?P" hence "?D" by blast}
  4706   moreover {assume nmi: "\<not> ?M" and npi: "\<not> ?P"
  4707     from rinf_\<Upsilon>[OF lp nmi npi] have "?F" using px by blast hence "?D" by blast}
  4708   ultimately show "?D" by blast
  4709 next
  4710   assume "?D" 
  4711   moreover {assume m:"?M" from rminusinf_ex[OF lp m] have "?E" .}
  4712   moreover {assume p: "?P" from rplusinf_ex[OF lp p] have "?E" . }
  4713   moreover {assume f:"?F" hence "?E" by blast}
  4714   ultimately show "?E" by blast
  4715 qed
  4716 
  4717 
  4718 lemma fr_eq\<upsilon>: 
  4719   assumes lp: "isrlfm p"
  4720   shows "(\<exists> x. Ifm (x#bs) p) = ((Ifm (x#bs) (minusinf p)) \<or> (Ifm (x#bs) (plusinf p)) \<or> (\<exists> (t,k) \<in> set (\<Upsilon> p). \<exists> (s,l) \<in> set (\<Upsilon> p). Ifm (x#bs) (\<upsilon> p (Add(Mul l t) (Mul k s) , 2*k*l))))"
  4721   (is "(\<exists> x. ?I x p) = (?M \<or> ?P \<or> ?F)" is "?E = ?D")
  4722 proof
  4723   assume px: "\<exists> x. ?I x p"
  4724   have "?M \<or> ?P \<or> (\<not> ?M \<and> \<not> ?P)" by blast
  4725   moreover {assume "?M \<or> ?P" hence "?D" by blast}
  4726   moreover {assume nmi: "\<not> ?M" and npi: "\<not> ?P"
  4727     let ?f ="\<lambda> (t,n). Inum (x#bs) t / real n"
  4728     let ?N = "\<lambda> t. Inum (x#bs) t"
  4729     {fix t n s m assume "(t,n)\<in> set (\<Upsilon> p)" and "(s,m) \<in> set (\<Upsilon> p)"
  4730       with \<Upsilon>_l[OF lp] have tnb: "numbound0 t" and np:"real n > 0" and snb: "numbound0 s" and mp:"real m > 0"
  4731         by auto
  4732       let ?st = "Add (Mul m t) (Mul n s)"
  4733       from mult_pos_pos[OF np mp] have mnp: "real (2*n*m) > 0" 
  4734         by (simp add: mult_commute)
  4735       from tnb snb have st_nb: "numbound0 ?st" by simp
  4736       have st: "(?N t / real n + ?N s / real m)/2 = ?N ?st / real (2*n*m)"
  4737         using mnp mp np by (simp add: algebra_simps add_divide_distrib)
  4738       from \<upsilon>_I[OF lp mnp st_nb, where x="x" and bs="bs"] 
  4739       have "?I x (\<upsilon> p (?st,2*n*m)) = ?I ((?N t / real n + ?N s / real m) /2) p" by (simp only: st[symmetric])}
  4740     with rinf_\<Upsilon>[OF lp nmi npi px] have "?F" by blast hence "?D" by blast}
  4741   ultimately show "?D" by blast
  4742 next
  4743   assume "?D" 
  4744   moreover {assume m:"?M" from rminusinf_ex[OF lp m] have "?E" .}
  4745   moreover {assume p: "?P" from rplusinf_ex[OF lp p] have "?E" . }
  4746   moreover {fix t k s l assume "(t,k) \<in> set (\<Upsilon> p)" and "(s,l) \<in> set (\<Upsilon> p)" 
  4747     and px:"?I x (\<upsilon> p (Add (Mul l t) (Mul k s), 2*k*l))"
  4748     with \<Upsilon>_l[OF lp] have tnb: "numbound0 t" and np:"real k > 0" and snb: "numbound0 s" and mp:"real l > 0" by auto
  4749     let ?st = "Add (Mul l t) (Mul k s)"
  4750     from mult_pos_pos[OF np mp] have mnp: "real (2*k*l) > 0" 
  4751       by (simp add: mult_commute)
  4752     from tnb snb have st_nb: "numbound0 ?st" by simp
  4753     from \<upsilon>_I[OF lp mnp st_nb, where bs="bs"] px have "?E" by auto}
  4754   ultimately show "?E" by blast
  4755 qed
  4756 
  4757 text{* The overall Part *}
  4758 
  4759 lemma real_ex_int_real01:
  4760   shows "(\<exists> (x::real). P x) = (\<exists> (i::int) (u::real). 0\<le> u \<and> u< 1 \<and> P (real i + u))"
  4761 proof(auto)
  4762   fix x
  4763   assume Px: "P x"
  4764   let ?i = "floor x"
  4765   let ?u = "x - real ?i"
  4766   have "x = real ?i + ?u" by simp
  4767   hence "P (real ?i + ?u)" using Px by simp
  4768   moreover have "real ?i \<le> x" using real_of_int_floor_le by simp hence "0 \<le> ?u" by arith
  4769   moreover have "?u < 1" using real_of_int_floor_add_one_gt[where r="x"] by arith 
  4770   ultimately show "(\<exists> (i::int) (u::real). 0\<le> u \<and> u< 1 \<and> P (real i + u))" by blast
  4771 qed
  4772 
  4773 fun exsplitnum :: "num \<Rightarrow> num" where
  4774   "exsplitnum (C c) = (C c)"
  4775 | "exsplitnum (Bound 0) = Add (Bound 0) (Bound 1)"
  4776 | "exsplitnum (Bound n) = Bound (n+1)"
  4777 | "exsplitnum (Neg a) = Neg (exsplitnum a)"
  4778 | "exsplitnum (Add a b) = Add (exsplitnum a) (exsplitnum b) "
  4779 | "exsplitnum (Sub a b) = Sub (exsplitnum a) (exsplitnum b) "
  4780 | "exsplitnum (Mul c a) = Mul c (exsplitnum a)"
  4781 | "exsplitnum (Floor a) = Floor (exsplitnum a)"
  4782 | "exsplitnum (CN 0 c a) = CN 0 c (Add (Mul c (Bound 1)) (exsplitnum a))"
  4783 | "exsplitnum (CN n c a) = CN (n+1) c (exsplitnum a)"
  4784 | "exsplitnum (CF c s t) = CF c (exsplitnum s) (exsplitnum t)"
  4785 
  4786 fun exsplit :: "fm \<Rightarrow> fm" where
  4787   "exsplit (Lt a) = Lt (exsplitnum a)"
  4788 | "exsplit (Le a) = Le (exsplitnum a)"
  4789 | "exsplit (Gt a) = Gt (exsplitnum a)"
  4790 | "exsplit (Ge a) = Ge (exsplitnum a)"
  4791 | "exsplit (Eq a) = Eq (exsplitnum a)"
  4792 | "exsplit (NEq a) = NEq (exsplitnum a)"
  4793 | "exsplit (Dvd i a) = Dvd i (exsplitnum a)"
  4794 | "exsplit (NDvd i a) = NDvd i (exsplitnum a)"
  4795 | "exsplit (And p q) = And (exsplit p) (exsplit q)"
  4796 | "exsplit (Or p q) = Or (exsplit p) (exsplit q)"
  4797 | "exsplit (Imp p q) = Imp (exsplit p) (exsplit q)"
  4798 | "exsplit (Iff p q) = Iff (exsplit p) (exsplit q)"
  4799 | "exsplit (NOT p) = NOT (exsplit p)"
  4800 | "exsplit p = p"
  4801 
  4802 lemma exsplitnum: 
  4803   "Inum (x#y#bs) (exsplitnum t) = Inum ((x+y) #bs) t"
  4804   by(induct t rule: exsplitnum.induct) (simp_all add: algebra_simps)
  4805 
  4806 lemma exsplit: 
  4807   assumes qfp: "qfree p"
  4808   shows "Ifm (x#y#bs) (exsplit p) = Ifm ((x+y)#bs) p"
  4809 using qfp exsplitnum[where x="x" and y="y" and bs="bs"]
  4810 by(induct p rule: exsplit.induct) simp_all
  4811 
  4812 lemma splitex:
  4813   assumes qf: "qfree p"
  4814   shows "(Ifm bs (E p)) = (\<exists> (i::int). Ifm (real i#bs) (E (And (And (Ge(CN 0 1 (C 0))) (Lt (CN 0 1 (C (- 1))))) (exsplit p))))" (is "?lhs = ?rhs")
  4815 proof-
  4816   have "?rhs = (\<exists> (i::int). \<exists> x. 0\<le> x \<and> x < 1 \<and> Ifm (x#(real i)#bs) (exsplit p))"
  4817     by (simp add: myless[of _ "1"] myless[of _ "0"] add_ac diff_minus)
  4818   also have "\<dots> = (\<exists> (i::int). \<exists> x. 0\<le> x \<and> x < 1 \<and> Ifm ((real i + x) #bs) p)"
  4819     by (simp only: exsplit[OF qf] add_ac)
  4820   also have "\<dots> = (\<exists> x. Ifm (x#bs) p)" 
  4821     by (simp only: real_ex_int_real01[where P="\<lambda> x. Ifm (x#bs) p"])
  4822   finally show ?thesis by simp
  4823 qed
  4824 
  4825     (* Implement the right hand sides of Cooper's theorem and Ferrante and Rackoff. *)
  4826 
  4827 definition ferrack01 :: "fm \<Rightarrow> fm" where
  4828   "ferrack01 p \<equiv> (let p' = rlfm(And (And (Ge(CN 0 1 (C 0))) (Lt (CN 0 1 (C (- 1))))) p);
  4829                     U = remdups(map simp_num_pair 
  4830                      (map (\<lambda> ((t,n),(s,m)). (Add (Mul m t) (Mul n s) , 2*n*m))
  4831                            (alluopairs (\<Upsilon> p')))) 
  4832   in decr (evaldjf (\<upsilon> p') U ))"
  4833 
  4834 lemma fr_eq_01: 
  4835   assumes qf: "qfree p"
  4836   shows "(\<exists> x. Ifm (x#bs) (And (And (Ge(CN 0 1 (C 0))) (Lt (CN 0 1 (C (- 1))))) p)) = (\<exists> (t,n) \<in> set (\<Upsilon> (rlfm (And (And (Ge(CN 0 1 (C 0))) (Lt (CN 0 1 (C (- 1))))) p))). \<exists> (s,m) \<in> set (\<Upsilon> (rlfm (And (And (Ge(CN 0 1 (C 0))) (Lt (CN 0 1 (C (- 1))))) p))). Ifm (x#bs) (\<upsilon> (rlfm (And (And (Ge(CN 0 1 (C 0))) (Lt (CN 0 1 (C (- 1))))) p)) (Add (Mul m t) (Mul n s), 2*n*m)))"
  4837   (is "(\<exists> x. ?I x ?q) = ?F")
  4838 proof-
  4839   let ?rq = "rlfm ?q"
  4840   let ?M = "?I x (minusinf ?rq)"
  4841   let ?P = "?I x (plusinf ?rq)"
  4842   have MF: "?M = False"
  4843     apply (simp add: Let_def reducecoeff_def numgcd_def rsplit_def ge_def lt_def conj_def disj_def)
  4844     by (cases "rlfm p = And (Ge (CN 0 1 (C 0))) (Lt (CN 0 1 (C -1)))", simp_all)
  4845   have PF: "?P = False" apply (simp add: Let_def reducecoeff_def numgcd_def rsplit_def ge_def lt_def conj_def disj_def)
  4846     by (cases "rlfm p = And (Ge (CN 0 1 (C 0))) (Lt (CN 0 1 (C -1)))", simp_all)
  4847   have "(\<exists> x. ?I x ?q ) = 
  4848     ((?I x (minusinf ?rq)) \<or> (?I x (plusinf ?rq )) \<or> (\<exists> (t,n) \<in> set (\<Upsilon> ?rq). \<exists> (s,m) \<in> set (\<Upsilon> ?rq ). ?I x (\<upsilon> ?rq (Add (Mul m t) (Mul n s), 2*n*m))))"
  4849     (is "(\<exists> x. ?I x ?q) = (?M \<or> ?P \<or> ?F)" is "?E = ?D")
  4850   proof
  4851     assume "\<exists> x. ?I x ?q"  
  4852     then obtain x where qx: "?I x ?q" by blast
  4853     hence xp: "0\<le> x" and x1: "x< 1" and px: "?I x p" 
  4854       by (auto simp add: rsplit_def lt_def ge_def rlfm_I[OF qf])
  4855     from qx have "?I x ?rq " 
  4856       by (simp add: rsplit_def lt_def ge_def rlfm_I[OF qf xp x1])
  4857     hence lqx: "?I x ?rq " using simpfm[where p="?rq" and bs="x#bs"] by auto
  4858     from qf have qfq:"isrlfm ?rq"  
  4859       by (auto simp add: rsplit_def lt_def ge_def rlfm_I[OF qf xp x1])
  4860     with lqx fr_eq\<upsilon>[OF qfq] show "?M \<or> ?P \<or> ?F" by blast
  4861   next
  4862     assume D: "?D"
  4863     let ?U = "set (\<Upsilon> ?rq )"
  4864     from MF PF D have "?F" by auto
  4865     then obtain t n s m where aU:"(t,n) \<in> ?U" and bU:"(s,m)\<in> ?U" and rqx: "?I x (\<upsilon> ?rq (Add (Mul m t) (Mul n s), 2*n*m))" by blast
  4866     from qf have lrq:"isrlfm ?rq"using rlfm_l[OF qf] 
  4867       by (auto simp add: rsplit_def lt_def ge_def)
  4868     from aU bU \<Upsilon>_l[OF lrq] have tnb: "numbound0 t" and np:"real n > 0" and snb: "numbound0 s" and mp:"real m > 0" by (auto simp add: split_def)
  4869     let ?st = "Add (Mul m t) (Mul n s)"
  4870     from tnb snb have stnb: "numbound0 ?st" by simp
  4871     from mult_pos_pos[OF np mp] have mnp: "real (2*n*m) > 0" 
  4872       by (simp add: mult_commute)
  4873     from conjunct1[OF \<upsilon>_I[OF lrq mnp stnb, where bs="bs" and x="x"], symmetric] rqx
  4874     have "\<exists> x. ?I x ?rq" by auto
  4875     thus "?E" 
  4876       using rlfm_I[OF qf] by (auto simp add: rsplit_def lt_def ge_def)
  4877   qed
  4878   with MF PF show ?thesis by blast
  4879 qed
  4880 
  4881 lemma \<Upsilon>_cong_aux:
  4882   assumes Ul: "\<forall> (t,n) \<in> set U. numbound0 t \<and> n >0"
  4883   shows "((\<lambda> (t,n). Inum (x#bs) t /real n) ` (set (map (\<lambda> ((t,n),(s,m)). (Add (Mul m t) (Mul n s) , 2*n*m)) (alluopairs U)))) = ((\<lambda> ((t,n),(s,m)). (Inum (x#bs) t /real n + Inum (x#bs) s /real m)/2) ` (set U \<times> set U))"
  4884   (is "?lhs = ?rhs")
  4885 proof(auto)
  4886   fix t n s m
  4887   assume "((t,n),(s,m)) \<in> set (alluopairs U)"
  4888   hence th: "((t,n),(s,m)) \<in> (set U \<times> set U)"
  4889     using alluopairs_set1[where xs="U"] by blast
  4890   let ?N = "\<lambda> t. Inum (x#bs) t"
  4891   let ?st= "Add (Mul m t) (Mul n s)"
  4892   from Ul th have mnz: "m \<noteq> 0" by auto
  4893   from Ul th have  nnz: "n \<noteq> 0" by auto  
  4894   have st: "(?N t / real n + ?N s / real m)/2 = ?N ?st / real (2*n*m)"
  4895    using mnz nnz by (simp add: algebra_simps add_divide_distrib)
  4896  
  4897   thus "(real m *  Inum (x # bs) t + real n * Inum (x # bs) s) /
  4898        (2 * real n * real m)
  4899        \<in> (\<lambda>((t, n), s, m).
  4900              (Inum (x # bs) t / real n + Inum (x # bs) s / real m) / 2) `
  4901          (set U \<times> set U)"using mnz nnz th  
  4902     apply (auto simp add: th add_divide_distrib algebra_simps split_def image_def)
  4903     by (rule_tac x="(s,m)" in bexI,simp_all) 
  4904   (rule_tac x="(t,n)" in bexI,simp_all add: mult_commute)
  4905 next
  4906   fix t n s m
  4907   assume tnU: "(t,n) \<in> set U" and smU:"(s,m) \<in> set U" 
  4908   let ?N = "\<lambda> t. Inum (x#bs) t"
  4909   let ?st= "Add (Mul m t) (Mul n s)"
  4910   from Ul smU have mnz: "m \<noteq> 0" by auto
  4911   from Ul tnU have  nnz: "n \<noteq> 0" by auto  
  4912   have st: "(?N t / real n + ?N s / real m)/2 = ?N ?st / real (2*n*m)"
  4913    using mnz nnz by (simp add: algebra_simps add_divide_distrib)
  4914  let ?P = "\<lambda> (t',n') (s',m'). (Inum (x # bs) t / real n + Inum (x # bs) s / real m)/2 = (Inum (x # bs) t' / real n' + Inum (x # bs) s' / real m')/2"
  4915  have Pc:"\<forall> a b. ?P a b = ?P b a"
  4916    by auto
  4917  from Ul alluopairs_set1 have Up:"\<forall> ((t,n),(s,m)) \<in> set (alluopairs U). n \<noteq> 0 \<and> m \<noteq> 0" by blast
  4918  from alluopairs_ex[OF Pc, where xs="U"] tnU smU
  4919  have th':"\<exists> ((t',n'),(s',m')) \<in> set (alluopairs U). ?P (t',n') (s',m')"
  4920    by blast
  4921  then obtain t' n' s' m' where ts'_U: "((t',n'),(s',m')) \<in> set (alluopairs U)" 
  4922    and Pts': "?P (t',n') (s',m')" by blast
  4923  from ts'_U Up have mnz': "m' \<noteq> 0" and nnz': "n'\<noteq> 0" by auto
  4924  let ?st' = "Add (Mul m' t') (Mul n' s')"
  4925    have st': "(?N t' / real n' + ?N s' / real m')/2 = ?N ?st' / real (2*n'*m')"
  4926    using mnz' nnz' by (simp add: algebra_simps add_divide_distrib)
  4927  from Pts' have 
  4928    "(Inum (x # bs) t / real n + Inum (x # bs) s / real m)/2 = (Inum (x # bs) t' / real n' + Inum (x # bs) s' / real m')/2" by simp
  4929  also have "\<dots> = ((\<lambda>(t, n). Inum (x # bs) t / real n) ((\<lambda>((t, n), s, m). (Add (Mul m t) (Mul n s), 2 * n * m)) ((t',n'),(s',m'))))" by (simp add: st')
  4930  finally show "(Inum (x # bs) t / real n + Inum (x # bs) s / real m) / 2
  4931           \<in> (\<lambda>(t, n). Inum (x # bs) t / real n) `
  4932             (\<lambda>((t, n), s, m). (Add (Mul m t) (Mul n s), 2 * n * m)) `
  4933             set (alluopairs U)"
  4934    using ts'_U by blast
  4935 qed
  4936 
  4937 lemma \<Upsilon>_cong:
  4938   assumes lp: "isrlfm p"
  4939   and UU': "((\<lambda> (t,n). Inum (x#bs) t /real n) ` U') = ((\<lambda> ((t,n),(s,m)). (Inum (x#bs) t /real n + Inum (x#bs) s /real m)/2) ` (U \<times> U))" (is "?f ` U' = ?g ` (U\<times>U)")
  4940   and U: "\<forall> (t,n) \<in> U. numbound0 t \<and> n > 0"
  4941   and U': "\<forall> (t,n) \<in> U'. numbound0 t \<and> n > 0"
  4942   shows "(\<exists> (t,n) \<in> U. \<exists> (s,m) \<in> U. Ifm (x#bs) (\<upsilon> p (Add (Mul m t) (Mul n s),2*n*m))) = (\<exists> (t,n) \<in> U'. Ifm (x#bs) (\<upsilon> p (t,n)))"
  4943   (is "?lhs = ?rhs")
  4944 proof
  4945   assume ?lhs
  4946   then obtain t n s m where tnU: "(t,n) \<in> U" and smU:"(s,m) \<in> U" and 
  4947     Pst: "Ifm (x#bs) (\<upsilon> p (Add (Mul m t) (Mul n s),2*n*m))" by blast
  4948   let ?N = "\<lambda> t. Inum (x#bs) t"
  4949   from tnU smU U have tnb: "numbound0 t" and np: "n > 0" 
  4950     and snb: "numbound0 s" and mp:"m > 0"  by auto
  4951   let ?st= "Add (Mul m t) (Mul n s)"
  4952   from mult_pos_pos[OF np mp] have mnp: "real (2*n*m) > 0" 
  4953       by (simp add: mult_commute real_of_int_mult[symmetric] del: real_of_int_mult)
  4954     from tnb snb have stnb: "numbound0 ?st" by simp
  4955   have st: "(?N t / real n + ?N s / real m)/2 = ?N ?st / real (2*n*m)"
  4956    using mp np by (simp add: algebra_simps add_divide_distrib)
  4957   from tnU smU UU' have "?g ((t,n),(s,m)) \<in> ?f ` U'" by blast
  4958   hence "\<exists> (t',n') \<in> U'. ?g ((t,n),(s,m)) = ?f (t',n')"
  4959     by auto (rule_tac x="(a,b)" in bexI, auto)
  4960   then obtain t' n' where tnU': "(t',n') \<in> U'" and th: "?g ((t,n),(s,m)) = ?f (t',n')" by blast
  4961   from U' tnU' have tnb': "numbound0 t'" and np': "real n' > 0" by auto
  4962   from \<upsilon>_I[OF lp mnp stnb, where bs="bs" and x="x"] Pst 
  4963   have Pst2: "Ifm (Inum (x # bs) (Add (Mul m t) (Mul n s)) / real (2 * n * m) # bs) p" by simp
  4964   from conjunct1[OF \<upsilon>_I[OF lp np' tnb', where bs="bs" and x="x"], symmetric] th[simplified split_def fst_conv snd_conv,symmetric] Pst2[simplified st[symmetric]]
  4965   have "Ifm (x # bs) (\<upsilon> p (t', n')) " by (simp only: st) 
  4966   then show ?rhs using tnU' by auto 
  4967 next
  4968   assume ?rhs
  4969   then obtain t' n' where tnU': "(t',n') \<in> U'" and Pt': "Ifm (x # bs) (\<upsilon> p (t', n'))" 
  4970     by blast
  4971   from tnU' UU' have "?f (t',n') \<in> ?g ` (U\<times>U)" by blast
  4972   hence "\<exists> ((t,n),(s,m)) \<in> (U\<times>U). ?f (t',n') = ?g ((t,n),(s,m))" 
  4973     by auto (rule_tac x="(a,b)" in bexI, auto)
  4974   then obtain t n s m where tnU: "(t,n) \<in> U" and smU:"(s,m) \<in> U" and 
  4975     th: "?f (t',n') = ?g((t,n),(s,m)) "by blast
  4976     let ?N = "\<lambda> t. Inum (x#bs) t"
  4977   from tnU smU U have tnb: "numbound0 t" and np: "n > 0" 
  4978     and snb: "numbound0 s" and mp:"m > 0"  by auto
  4979   let ?st= "Add (Mul m t) (Mul n s)"
  4980   from mult_pos_pos[OF np mp] have mnp: "real (2*n*m) > 0" 
  4981       by (simp add: mult_commute real_of_int_mult[symmetric] del: real_of_int_mult)
  4982     from tnb snb have stnb: "numbound0 ?st" by simp
  4983   have st: "(?N t / real n + ?N s / real m)/2 = ?N ?st / real (2*n*m)"
  4984    using mp np by (simp add: algebra_simps add_divide_distrib)
  4985   from U' tnU' have tnb': "numbound0 t'" and np': "real n' > 0" by auto
  4986   from \<upsilon>_I[OF lp np' tnb', where bs="bs" and x="x",simplified th[simplified split_def fst_conv snd_conv] st] Pt'
  4987   have Pst2: "Ifm (Inum (x # bs) (Add (Mul m t) (Mul n s)) / real (2 * n * m) # bs) p" by simp
  4988   with \<upsilon>_I[OF lp mnp stnb, where x="x" and bs="bs"] tnU smU show ?lhs by blast
  4989 qed
  4990   
  4991 lemma ferrack01: 
  4992   assumes qf: "qfree p"
  4993   shows "((\<exists> x. Ifm (x#bs) (And (And (Ge(CN 0 1 (C 0))) (Lt (CN 0 1 (C (- 1))))) p)) = (Ifm bs (ferrack01 p))) \<and> qfree (ferrack01 p)" (is "(?lhs = ?rhs) \<and> _")
  4994 proof-
  4995   let ?I = "\<lambda> x p. Ifm (x#bs) p"
  4996   fix x
  4997   let ?N = "\<lambda> t. Inum (x#bs) t"
  4998   let ?q = "rlfm (And (And (Ge(CN 0 1 (C 0))) (Lt (CN 0 1 (C (- 1))))) p)"
  4999   let ?U = "\<Upsilon> ?q"
  5000   let ?Up = "alluopairs ?U"
  5001   let ?g = "\<lambda> ((t,n),(s,m)). (Add (Mul m t) (Mul n s) , 2*n*m)"
  5002   let ?S = "map ?g ?Up"
  5003   let ?SS = "map simp_num_pair ?S"
  5004   let ?Y = "remdups ?SS"
  5005   let ?f= "(\<lambda> (t,n). ?N t / real n)"
  5006   let ?h = "\<lambda> ((t,n),(s,m)). (?N t/real n + ?N s/ real m) /2"
  5007   let ?F = "\<lambda> p. \<exists> a \<in> set (\<Upsilon> p). \<exists> b \<in> set (\<Upsilon> p). ?I x (\<upsilon> p (?g(a,b)))"
  5008   let ?ep = "evaldjf (\<upsilon> ?q) ?Y"
  5009   from rlfm_l[OF qf] have lq: "isrlfm ?q" 
  5010     by (simp add: rsplit_def lt_def ge_def conj_def disj_def Let_def reducecoeff_def numgcd_def)
  5011   from alluopairs_set1[where xs="?U"] have UpU: "set ?Up \<le> (set ?U \<times> set ?U)" by simp
  5012   from \<Upsilon>_l[OF lq] have U_l: "\<forall> (t,n) \<in> set ?U. numbound0 t \<and> n > 0" .
  5013   from U_l UpU 
  5014   have Up_: "\<forall> ((t,n),(s,m)) \<in> set ?Up. numbound0 t \<and> n> 0 \<and> numbound0 s \<and> m > 0" by auto
  5015   hence Snb: "\<forall> (t,n) \<in> set ?S. numbound0 t \<and> n > 0 "
  5016     by (auto simp add: mult_pos_pos)
  5017   have Y_l: "\<forall> (t,n) \<in> set ?Y. numbound0 t \<and> n > 0" 
  5018   proof-
  5019     { fix t n assume tnY: "(t,n) \<in> set ?Y" 
  5020       hence "(t,n) \<in> set ?SS" by simp
  5021       hence "\<exists> (t',n') \<in> set ?S. simp_num_pair (t',n') = (t,n)"
  5022         by (auto simp add: split_def simp del: map_map)
  5023            (rule_tac x="((aa,ba),(ab,bb))" in bexI, simp_all)
  5024       then obtain t' n' where tn'S: "(t',n') \<in> set ?S" and tns: "simp_num_pair (t',n') = (t,n)" by blast
  5025       from tn'S Snb have tnb: "numbound0 t'" and np: "n' > 0" by auto
  5026       from simp_num_pair_l[OF tnb np tns]
  5027       have "numbound0 t \<and> n > 0" . }
  5028     thus ?thesis by blast
  5029   qed
  5030 
  5031   have YU: "(?f ` set ?Y) = (?h ` (set ?U \<times> set ?U))"
  5032   proof-
  5033      from simp_num_pair_ci[where bs="x#bs"] have 
  5034     "\<forall>x. (?f o simp_num_pair) x = ?f x" by auto
  5035      hence th: "?f o simp_num_pair = ?f" using ext by blast
  5036     have "(?f ` set ?Y) = ((?f o simp_num_pair) ` set ?S)" by (simp add: image_compose)
  5037     also have "\<dots> = (?f ` set ?S)" by (simp add: th)
  5038     also have "\<dots> = ((?f o ?g) ` set ?Up)" 
  5039       by (simp only: set_map o_def image_compose[symmetric])
  5040     also have "\<dots> = (?h ` (set ?U \<times> set ?U))"
  5041       using \<Upsilon>_cong_aux[OF U_l, where x="x" and bs="bs", simplified set_map image_compose[symmetric]] by blast
  5042     finally show ?thesis .
  5043   qed
  5044   have "\<forall> (t,n) \<in> set ?Y. bound0 (\<upsilon> ?q (t,n))"
  5045   proof-
  5046     { fix t n assume tnY: "(t,n) \<in> set ?Y"
  5047       with Y_l have tnb: "numbound0 t" and np: "real n > 0" by auto
  5048       from \<upsilon>_I[OF lq np tnb]
  5049     have "bound0 (\<upsilon> ?q (t,n))"  by simp}
  5050     thus ?thesis by blast
  5051   qed
  5052   hence ep_nb: "bound0 ?ep"  using evaldjf_bound0[where xs="?Y" and f="\<upsilon> ?q"]
  5053     by auto
  5054 
  5055   from fr_eq_01[OF qf, where bs="bs" and x="x"] have "?lhs = ?F ?q"
  5056     by (simp only: split_def fst_conv snd_conv)
  5057   also have "\<dots> = (\<exists> (t,n) \<in> set ?Y. ?I x (\<upsilon> ?q (t,n)))" using \<Upsilon>_cong[OF lq YU U_l Y_l]
  5058     by (simp only: split_def fst_conv snd_conv) 
  5059   also have "\<dots> = (Ifm (x#bs) ?ep)" 
  5060     using evaldjf_ex[where ps="?Y" and bs = "x#bs" and f="\<upsilon> ?q",symmetric]
  5061     by (simp only: split_def pair_collapse)
  5062   also have "\<dots> = (Ifm bs (decr ?ep))" using decr[OF ep_nb] by blast
  5063   finally have lr: "?lhs = ?rhs" by (simp only: ferrack01_def Let_def)
  5064   from decr_qf[OF ep_nb] have "qfree (ferrack01 p)" by (simp only: Let_def ferrack01_def)
  5065   with lr show ?thesis by blast
  5066 qed
  5067 
  5068 lemma cp_thm': 
  5069   assumes lp: "iszlfm p (real (i::int)#bs)"
  5070   and up: "d\<beta> p 1" and dd: "d\<delta> p d" and dp: "d > 0"
  5071   shows "(\<exists> (x::int). Ifm (real x#bs) p) = ((\<exists> j\<in> {1 .. d}. Ifm (real j#bs) (minusinf p)) \<or> (\<exists> j\<in> {1.. d}. \<exists> b\<in> (Inum (real i#bs)) ` set (\<beta> p). Ifm ((b+real j)#bs) p))"
  5072   using cp_thm[OF lp up dd dp] by auto
  5073 
  5074 definition unit :: "fm \<Rightarrow> fm \<times> num list \<times> int" where
  5075   "unit p \<equiv> (let p' = zlfm p ; l = \<zeta> p' ; q = And (Dvd l (CN 0 1 (C 0))) (a\<beta> p' l); d = \<delta> q;
  5076              B = remdups (map simpnum (\<beta> q)) ; a = remdups (map simpnum (\<alpha> q))
  5077              in if length B \<le> length a then (q,B,d) else (mirror q, a,d))"
  5078 
  5079 lemma unit: assumes qf: "qfree p"
  5080   shows "\<And> q B d. unit p = (q,B,d) \<Longrightarrow> ((\<exists> (x::int). Ifm (real x#bs) p) = (\<exists> (x::int). Ifm (real x#bs) q)) \<and> (Inum (real i#bs)) ` set B = (Inum (real i#bs)) ` set (\<beta> q) \<and> d\<beta> q 1 \<and> d\<delta> q d \<and> d >0 \<and> iszlfm q (real (i::int)#bs) \<and> (\<forall> b\<in> set B. numbound0 b)"
  5081 proof-
  5082   fix q B d 
  5083   assume qBd: "unit p = (q,B,d)"
  5084   let ?thes = "((\<exists> (x::int). Ifm (real x#bs) p) = (\<exists> (x::int). Ifm (real x#bs) q)) \<and>
  5085     Inum (real i#bs) ` set B = Inum (real i#bs) ` set (\<beta> q) \<and>
  5086     d\<beta> q 1 \<and> d\<delta> q d \<and> 0 < d \<and> iszlfm q (real i # bs) \<and> (\<forall> b\<in> set B. numbound0 b)"
  5087   let ?I = "\<lambda> (x::int) p. Ifm (real x#bs) p"
  5088   let ?p' = "zlfm p"
  5089   let ?l = "\<zeta> ?p'"
  5090   let ?q = "And (Dvd ?l (CN 0 1 (C 0))) (a\<beta> ?p' ?l)"
  5091   let ?d = "\<delta> ?q"
  5092   let ?B = "set (\<beta> ?q)"
  5093   let ?B'= "remdups (map simpnum (\<beta> ?q))"
  5094   let ?A = "set (\<alpha> ?q)"
  5095   let ?A'= "remdups (map simpnum (\<alpha> ?q))"
  5096   from conjunct1[OF zlfm_I[OF qf, where bs="bs"]] 
  5097   have pp': "\<forall> i. ?I i ?p' = ?I i p" by auto
  5098   from iszlfm_gen[OF conjunct2[OF zlfm_I[OF qf, where bs="bs" and i="i"]]]
  5099   have lp': "\<forall> (i::int). iszlfm ?p' (real i#bs)" by simp 
  5100   hence lp'': "iszlfm ?p' (real (i::int)#bs)" by simp
  5101   from lp' \<zeta>[where p="?p'" and bs="bs"] have lp: "?l >0" and dl: "d\<beta> ?p' ?l" by auto
  5102   from a\<beta>_ex[where p="?p'" and l="?l" and bs="bs", OF lp'' dl lp] pp'
  5103   have pq_ex:"(\<exists> (x::int). ?I x p) = (\<exists> x. ?I x ?q)" by (simp add: int_rdvd_iff) 
  5104   from lp'' lp a\<beta>[OF lp'' dl lp] have lq:"iszlfm ?q (real i#bs)" and uq: "d\<beta> ?q 1" 
  5105     by (auto simp add: isint_def)
  5106   from \<delta>[OF lq] have dp:"?d >0" and dd: "d\<delta> ?q ?d" by blast+
  5107   let ?N = "\<lambda> t. Inum (real (i::int)#bs) t"
  5108   have "?N ` set ?B' = ((?N o simpnum) ` ?B)" by (simp add:image_compose) 
  5109   also have "\<dots> = ?N ` ?B" using simpnum_ci[where bs="real i #bs"] by auto
  5110   finally have BB': "?N ` set ?B' = ?N ` ?B" .
  5111   have "?N ` set ?A' = ((?N o simpnum) ` ?A)" by (simp add:image_compose) 
  5112   also have "\<dots> = ?N ` ?A" using simpnum_ci[where bs="real i #bs"] by auto
  5113   finally have AA': "?N ` set ?A' = ?N ` ?A" .
  5114   from \<beta>_numbound0[OF lq] have B_nb:"\<forall> b\<in> set ?B'. numbound0 b"
  5115     by (simp add: simpnum_numbound0)
  5116   from \<alpha>_l[OF lq] have A_nb: "\<forall> b\<in> set ?A'. numbound0 b"
  5117     by (simp add: simpnum_numbound0)
  5118     {assume "length ?B' \<le> length ?A'"
  5119     hence q:"q=?q" and "B = ?B'" and d:"d = ?d"
  5120       using qBd by (auto simp add: Let_def unit_def)
  5121     with BB' B_nb have b: "?N ` (set B) = ?N ` set (\<beta> q)" 
  5122       and bn: "\<forall>b\<in> set B. numbound0 b" by simp+ 
  5123   with pq_ex dp uq dd lq q d have ?thes by simp}
  5124   moreover 
  5125   {assume "\<not> (length ?B' \<le> length ?A')"
  5126     hence q:"q=mirror ?q" and "B = ?A'" and d:"d = ?d"
  5127       using qBd by (auto simp add: Let_def unit_def)
  5128     with AA' mirror\<alpha>\<beta>[OF lq] A_nb have b:"?N ` (set B) = ?N ` set (\<beta> q)" 
  5129       and bn: "\<forall>b\<in> set B. numbound0 b" by simp+
  5130     from mirror_ex[OF lq] pq_ex q 
  5131     have pqm_eq:"(\<exists> (x::int). ?I x p) = (\<exists> (x::int). ?I x q)" by simp
  5132     from lq uq q mirror_d\<beta> [where p="?q" and bs="bs" and a="real i"]
  5133     have lq': "iszlfm q (real i#bs)" and uq: "d\<beta> q 1" by auto
  5134     from \<delta>[OF lq'] mirror_\<delta>[OF lq] q d have dq:"d\<delta> q d " by auto
  5135     from pqm_eq b bn uq lq' dp dq q dp d have ?thes by simp
  5136   }
  5137   ultimately show ?thes by blast
  5138 qed
  5139     (* Cooper's Algorithm *)
  5140 
  5141 definition cooper :: "fm \<Rightarrow> fm" where
  5142   "cooper p \<equiv> 
  5143   (let (q,B,d) = unit p; js = [1..d];
  5144        mq = simpfm (minusinf q);
  5145        md = evaldjf (\<lambda> j. simpfm (subst0 (C j) mq)) js
  5146    in if md = T then T else
  5147     (let qd = evaldjf (\<lambda> t. simpfm (subst0 t q)) 
  5148                                (remdups (map (\<lambda> (b,j). simpnum (Add b (C j))) 
  5149                                             [(b,j). b\<leftarrow>B,j\<leftarrow>js]))
  5150      in decr (disj md qd)))"
  5151 lemma cooper: assumes qf: "qfree p"
  5152   shows "((\<exists> (x::int). Ifm (real x#bs) p) = (Ifm bs (cooper p))) \<and> qfree (cooper p)" 
  5153   (is "(?lhs = ?rhs) \<and> _")
  5154 proof-
  5155 
  5156   let ?I = "\<lambda> (x::int) p. Ifm (real x#bs) p"
  5157   let ?q = "fst (unit p)"
  5158   let ?B = "fst (snd(unit p))"
  5159   let ?d = "snd (snd (unit p))"
  5160   let ?js = "[1..?d]"
  5161   let ?mq = "minusinf ?q"
  5162   let ?smq = "simpfm ?mq"
  5163   let ?md = "evaldjf (\<lambda> j. simpfm (subst0 (C j) ?smq)) ?js"
  5164   fix i
  5165   let ?N = "\<lambda> t. Inum (real (i::int)#bs) t"
  5166   let ?bjs = "[(b,j). b\<leftarrow>?B,j\<leftarrow>?js]"
  5167   let ?sbjs = "map (\<lambda> (b,j). simpnum (Add b (C j))) ?bjs"
  5168   let ?qd = "evaldjf (\<lambda> t. simpfm (subst0 t ?q)) (remdups ?sbjs)"
  5169   have qbf:"unit p = (?q,?B,?d)" by simp
  5170   from unit[OF qf qbf] have pq_ex: "(\<exists>(x::int). ?I x p) = (\<exists> (x::int). ?I x ?q)" and 
  5171     B:"?N ` set ?B = ?N ` set (\<beta> ?q)" and 
  5172     uq:"d\<beta> ?q 1" and dd: "d\<delta> ?q ?d" and dp: "?d > 0" and 
  5173     lq: "iszlfm ?q (real i#bs)" and 
  5174     Bn: "\<forall> b\<in> set ?B. numbound0 b" by auto
  5175   from zlin_qfree[OF lq] have qfq: "qfree ?q" .
  5176   from simpfm_qf[OF minusinf_qfree[OF qfq]] have qfmq: "qfree ?smq".
  5177   have jsnb: "\<forall> j \<in> set ?js. numbound0 (C j)" by simp
  5178   hence "\<forall> j\<in> set ?js. bound0 (subst0 (C j) ?smq)" 
  5179     by (auto simp only: subst0_bound0[OF qfmq])
  5180   hence th: "\<forall> j\<in> set ?js. bound0 (simpfm (subst0 (C j) ?smq))"
  5181     by (auto simp add: simpfm_bound0)
  5182   from evaldjf_bound0[OF th] have mdb: "bound0 ?md" by simp 
  5183   from Bn jsnb have "\<forall> (b,j) \<in> set ?bjs. numbound0 (Add b (C j))"
  5184     by simp
  5185   hence "\<forall> (b,j) \<in> set ?bjs. numbound0 (simpnum (Add b (C j)))"
  5186     using simpnum_numbound0 by blast
  5187   hence "\<forall> t \<in> set ?sbjs. numbound0 t" by simp
  5188   hence "\<forall> t \<in> set (remdups ?sbjs). bound0 (subst0 t ?q)"
  5189     using subst0_bound0[OF qfq] by auto 
  5190   hence th': "\<forall> t \<in> set (remdups ?sbjs). bound0 (simpfm (subst0 t ?q))"
  5191     using simpfm_bound0 by blast
  5192   from evaldjf_bound0 [OF th'] have qdb: "bound0 ?qd" by simp
  5193   from mdb qdb 
  5194   have mdqdb: "bound0 (disj ?md ?qd)" by (simp only: disj_def, cases "?md=T \<or> ?qd=T", simp_all)
  5195   from trans [OF pq_ex cp_thm'[OF lq uq dd dp]] B
  5196   have "?lhs = (\<exists> j\<in> {1.. ?d}. ?I j ?mq \<or> (\<exists> b\<in> ?N ` set ?B. Ifm ((b+ real j)#bs) ?q))" by auto
  5197   also have "\<dots> = ((\<exists> j\<in> set ?js. ?I j ?smq) \<or> (\<exists> (b,j) \<in> (?N ` set ?B \<times> set ?js). Ifm ((b+ real j)#bs) ?q))" by auto
  5198   also have "\<dots>= ((\<exists> j\<in> set ?js. ?I j ?smq) \<or> (\<exists> t \<in> (\<lambda> (b,j). ?N (Add b (C j))) ` set ?bjs. Ifm (t #bs) ?q))" by simp
  5199   also have "\<dots>= ((\<exists> j\<in> set ?js. ?I j ?smq) \<or> (\<exists> t \<in> (\<lambda> (b,j). ?N (simpnum (Add b (C j)))) ` set ?bjs. Ifm (t #bs) ?q))" by (simp only: simpnum_ci)
  5200   also  have "\<dots>= ((\<exists> j\<in> set ?js. ?I j ?smq) \<or> (\<exists> t \<in> set ?sbjs. Ifm (?N t #bs) ?q))" 
  5201     by (auto simp add: split_def) 
  5202   also have "\<dots> = ((\<exists> j\<in> set ?js. (\<lambda> j. ?I i (simpfm (subst0 (C j) ?smq))) j) \<or> (\<exists> t \<in> set (remdups ?sbjs). (\<lambda> t. ?I i (simpfm (subst0 t ?q))) t))" by (simp only: simpfm subst0_I[OF qfq] simpfm Inum.simps subst0_I[OF qfmq] set_remdups)
  5203   also have "\<dots> = ((?I i (evaldjf (\<lambda> j. simpfm (subst0 (C j) ?smq)) ?js)) \<or> (?I i (evaldjf (\<lambda> t. simpfm (subst0 t ?q)) (remdups ?sbjs))))" by (simp only: evaldjf_ex)
  5204   finally have mdqd: "?lhs = (?I i (disj ?md ?qd))" by (simp add: disj) 
  5205   hence mdqd2: "?lhs = (Ifm bs (decr (disj ?md ?qd)))" using decr [OF mdqdb] by simp
  5206   {assume mdT: "?md = T"
  5207     hence cT:"cooper p = T" 
  5208       by (simp only: cooper_def unit_def split_def Let_def if_True) simp
  5209     from mdT mdqd have lhs:"?lhs" by (auto simp add: disj)
  5210     from mdT have "?rhs" by (simp add: cooper_def unit_def split_def)
  5211     with lhs cT have ?thesis by simp }
  5212   moreover
  5213   {assume mdT: "?md \<noteq> T" hence "cooper p = decr (disj ?md ?qd)" 
  5214       by (simp only: cooper_def unit_def split_def Let_def if_False) 
  5215     with mdqd2 decr_qf[OF mdqdb] have ?thesis by simp }
  5216   ultimately show ?thesis by blast
  5217 qed
  5218 
  5219 lemma DJcooper: 
  5220   assumes qf: "qfree p"
  5221   shows "((\<exists> (x::int). Ifm (real x#bs) p) = (Ifm bs (DJ cooper p))) \<and> qfree (DJ cooper p)"
  5222 proof-
  5223   from cooper have cqf: "\<forall> p. qfree p \<longrightarrow> qfree (cooper p)" by  blast
  5224   from DJ_qf[OF cqf] qf have thqf:"qfree (DJ cooper p)" by blast
  5225   have "Ifm bs (DJ cooper p) = (\<exists> q\<in> set (disjuncts p). Ifm bs (cooper q))" 
  5226      by (simp add: DJ_def evaldjf_ex)
  5227   also have "\<dots> = (\<exists> q \<in> set(disjuncts p). \<exists> (x::int). Ifm (real x#bs)  q)" 
  5228     using cooper disjuncts_qf[OF qf] by blast
  5229   also have "\<dots> = (\<exists> (x::int). Ifm (real x#bs) p)" by (induct p rule: disjuncts.induct, auto)
  5230   finally show ?thesis using thqf by blast
  5231 qed
  5232 
  5233     (* Redy and Loveland *)
  5234 
  5235 lemma \<sigma>\<rho>_cong: assumes lp: "iszlfm p (a#bs)" and tt': "Inum (a#bs) t = Inum (a#bs) t'"
  5236   shows "Ifm (a#bs) (\<sigma>\<rho> p (t,c)) = Ifm (a#bs) (\<sigma>\<rho> p (t',c))"
  5237   using lp 
  5238   by (induct p rule: iszlfm.induct, auto simp add: tt')
  5239 
  5240 lemma \<sigma>_cong: assumes lp: "iszlfm p (a#bs)" and tt': "Inum (a#bs) t = Inum (a#bs) t'"
  5241   shows "Ifm (a#bs) (\<sigma> p c t) = Ifm (a#bs) (\<sigma> p c t')"
  5242   by (simp add: \<sigma>_def tt' \<sigma>\<rho>_cong[OF lp tt'])
  5243 
  5244 lemma \<rho>_cong: assumes lp: "iszlfm p (a#bs)" 
  5245   and RR: "(\<lambda>(b,k). (Inum (a#bs) b,k)) ` R =  (\<lambda>(b,k). (Inum (a#bs) b,k)) ` set (\<rho> p)"
  5246   shows "(\<exists> (e,c) \<in> R. \<exists> j\<in> {1.. c*(\<delta> p)}. Ifm (a#bs) (\<sigma> p c (Add e (C j)))) = (\<exists> (e,c) \<in> set (\<rho> p). \<exists> j\<in> {1.. c*(\<delta> p)}. Ifm (a#bs) (\<sigma> p c (Add e (C j))))"
  5247   (is "?lhs = ?rhs")
  5248 proof
  5249   let ?d = "\<delta> p"
  5250   assume ?lhs then obtain e c j where ecR: "(e,c) \<in> R" and jD:"j \<in> {1 .. c*?d}" 
  5251     and px: "Ifm (a#bs) (\<sigma> p c (Add e (C j)))" (is "?sp c e j") by blast
  5252   from ecR have "(Inum (a#bs) e,c) \<in> (\<lambda>(b,k). (Inum (a#bs) b,k)) ` R" by auto
  5253   hence "(Inum (a#bs) e,c) \<in> (\<lambda>(b,k). (Inum (a#bs) b,k)) ` set (\<rho> p)" using RR by simp
  5254   hence "\<exists> (e',c') \<in> set (\<rho> p). Inum (a#bs) e = Inum (a#bs) e' \<and> c = c'" by auto
  5255   then obtain e' c' where ecRo:"(e',c') \<in> set (\<rho> p)" and ee':"Inum (a#bs) e = Inum (a#bs) e'"
  5256     and cc':"c = c'" by blast
  5257   from ee' have tt': "Inum (a#bs) (Add e (C j)) = Inum (a#bs) (Add e' (C j))" by simp
  5258   
  5259   from \<sigma>_cong[OF lp tt', where c="c"] px have px':"?sp c e' j" by simp
  5260   from ecRo jD px' cc'  show ?rhs apply auto 
  5261     by (rule_tac x="(e', c')" in bexI,simp_all)
  5262   (rule_tac x="j" in bexI, simp_all add: cc'[symmetric])
  5263 next
  5264   let ?d = "\<delta> p"
  5265   assume ?rhs then obtain e c j where ecR: "(e,c) \<in> set (\<rho> p)" and jD:"j \<in> {1 .. c*?d}" 
  5266     and px: "Ifm (a#bs) (\<sigma> p c (Add e (C j)))" (is "?sp c e j") by blast
  5267   from ecR have "(Inum (a#bs) e,c) \<in> (\<lambda>(b,k). (Inum (a#bs) b,k)) ` set (\<rho> p)" by auto
  5268   hence "(Inum (a#bs) e,c) \<in> (\<lambda>(b,k). (Inum (a#bs) b,k)) ` R" using RR by simp
  5269   hence "\<exists> (e',c') \<in> R. Inum (a#bs) e = Inum (a#bs) e' \<and> c = c'" by auto
  5270   then obtain e' c' where ecRo:"(e',c') \<in> R" and ee':"Inum (a#bs) e = Inum (a#bs) e'"
  5271     and cc':"c = c'" by blast
  5272   from ee' have tt': "Inum (a#bs) (Add e (C j)) = Inum (a#bs) (Add e' (C j))" by simp
  5273   from \<sigma>_cong[OF lp tt', where c="c"] px have px':"?sp c e' j" by simp
  5274   from ecRo jD px' cc'  show ?lhs apply auto 
  5275     by (rule_tac x="(e', c')" in bexI,simp_all)
  5276   (rule_tac x="j" in bexI, simp_all add: cc'[symmetric])
  5277 qed
  5278 
  5279 lemma rl_thm': 
  5280   assumes lp: "iszlfm p (real (i::int)#bs)" 
  5281   and R: "(\<lambda>(b,k). (Inum (a#bs) b,k)) ` R =  (\<lambda>(b,k). (Inum (a#bs) b,k)) ` set (\<rho> p)"
  5282   shows "(\<exists> (x::int). Ifm (real x#bs) p) = ((\<exists> j\<in> {1 .. \<delta> p}. Ifm (real j#bs) (minusinf p)) \<or> (\<exists> (e,c) \<in> R. \<exists> j\<in> {1.. c*(\<delta> p)}. Ifm (a#bs) (\<sigma> p c (Add e (C j)))))"
  5283   using rl_thm[OF lp] \<rho>_cong[OF iszlfm_gen[OF lp, rule_format, where y="a"] R] by simp 
  5284 
  5285 definition chooset :: "fm \<Rightarrow> fm \<times> ((num\<times>int) list) \<times> int" where
  5286   "chooset p \<equiv> (let q = zlfm p ; d = \<delta> q;
  5287              B = remdups (map (\<lambda> (t,k). (simpnum t,k)) (\<rho> q)) ; 
  5288              a = remdups (map (\<lambda> (t,k). (simpnum t,k)) (\<alpha>\<rho> q))
  5289              in if length B \<le> length a then (q,B,d) else (mirror q, a,d))"
  5290 
  5291 lemma chooset: assumes qf: "qfree p"
  5292   shows "\<And> q B d. chooset p = (q,B,d) \<Longrightarrow> ((\<exists> (x::int). Ifm (real x#bs) p) = (\<exists> (x::int). Ifm (real x#bs) q)) \<and> ((\<lambda>(t,k). (Inum (real i#bs) t,k)) ` set B = (\<lambda>(t,k). (Inum (real i#bs) t,k)) ` set (\<rho> q)) \<and> (\<delta> q = d) \<and> d >0 \<and> iszlfm q (real (i::int)#bs) \<and> (\<forall> (e,c)\<in> set B. numbound0 e \<and> c>0)"
  5293 proof-
  5294   fix q B d 
  5295   assume qBd: "chooset p = (q,B,d)"
  5296   let ?thes = "((\<exists> (x::int). Ifm (real x#bs) p) = (\<exists> (x::int). Ifm (real x#bs) q)) \<and> ((\<lambda>(t,k). (Inum (real i#bs) t,k)) ` set B = (\<lambda>(t,k). (Inum (real i#bs) t,k)) ` set (\<rho> q)) \<and> (\<delta> q = d) \<and> d >0 \<and> iszlfm q (real (i::int)#bs) \<and> (\<forall> (e,c)\<in> set B. numbound0 e \<and> c>0)" 
  5297   let ?I = "\<lambda> (x::int) p. Ifm (real x#bs) p"
  5298   let ?q = "zlfm p"
  5299   let ?d = "\<delta> ?q"
  5300   let ?B = "set (\<rho> ?q)"
  5301   let ?f = "\<lambda> (t,k). (simpnum t,k)"
  5302   let ?B'= "remdups (map ?f (\<rho> ?q))"
  5303   let ?A = "set (\<alpha>\<rho> ?q)"
  5304   let ?A'= "remdups (map ?f (\<alpha>\<rho> ?q))"
  5305   from conjunct1[OF zlfm_I[OF qf, where bs="bs"]] 
  5306   have pp': "\<forall> i. ?I i ?q = ?I i p" by auto
  5307   hence pq_ex:"(\<exists> (x::int). ?I x p) = (\<exists> x. ?I x ?q)" by simp 
  5308   from iszlfm_gen[OF conjunct2[OF zlfm_I[OF qf, where bs="bs" and i="i"]], rule_format, where y="real i"]
  5309   have lq: "iszlfm ?q (real (i::int)#bs)" . 
  5310   from \<delta>[OF lq] have dp:"?d >0" by blast
  5311   let ?N = "\<lambda> (t,c). (Inum (real (i::int)#bs) t,c)"
  5312   have "?N ` set ?B' = ((?N o ?f) ` ?B)" by (simp add: split_def image_compose)
  5313   also have "\<dots> = ?N ` ?B"
  5314     by(simp add: split_def image_compose simpnum_ci[where bs="real i #bs"] image_def)
  5315   finally have BB': "?N ` set ?B' = ?N ` ?B" .
  5316   have "?N ` set ?A' = ((?N o ?f) ` ?A)" by (simp add: split_def image_compose) 
  5317   also have "\<dots> = ?N ` ?A" using simpnum_ci[where bs="real i #bs"]
  5318     by(simp add: split_def image_compose simpnum_ci[where bs="real i #bs"] image_def) 
  5319   finally have AA': "?N ` set ?A' = ?N ` ?A" .
  5320   from \<rho>_l[OF lq] have B_nb:"\<forall> (e,c)\<in> set ?B'. numbound0 e \<and> c > 0"
  5321     by (simp add: simpnum_numbound0 split_def)
  5322   from \<alpha>\<rho>_l[OF lq] have A_nb: "\<forall> (e,c)\<in> set ?A'. numbound0 e \<and> c > 0"
  5323     by (simp add: simpnum_numbound0 split_def)
  5324     {assume "length ?B' \<le> length ?A'"
  5325     hence q:"q=?q" and "B = ?B'" and d:"d = ?d"
  5326       using qBd by (auto simp add: Let_def chooset_def)
  5327     with BB' B_nb have b: "?N ` (set B) = ?N ` set (\<rho> q)" 
  5328       and bn: "\<forall>(e,c)\<in> set B. numbound0 e \<and> c > 0" by auto
  5329   with pq_ex dp lq q d have ?thes by simp}
  5330   moreover 
  5331   {assume "\<not> (length ?B' \<le> length ?A')"
  5332     hence q:"q=mirror ?q" and "B = ?A'" and d:"d = ?d"
  5333       using qBd by (auto simp add: Let_def chooset_def)
  5334     with AA' mirror_\<alpha>\<rho>[OF lq] A_nb have b:"?N ` (set B) = ?N ` set (\<rho> q)" 
  5335       and bn: "\<forall>(e,c)\<in> set B. numbound0 e \<and> c > 0" by auto 
  5336     from mirror_ex[OF lq] pq_ex q 
  5337     have pqm_eq:"(\<exists> (x::int). ?I x p) = (\<exists> (x::int). ?I x q)" by simp
  5338     from lq q mirror_l [where p="?q" and bs="bs" and a="real i"]
  5339     have lq': "iszlfm q (real i#bs)" by auto
  5340     from mirror_\<delta>[OF lq] pqm_eq b bn lq' dp q dp d have ?thes by simp
  5341   }
  5342   ultimately show ?thes by blast
  5343 qed
  5344 
  5345 definition stage :: "fm \<Rightarrow> int \<Rightarrow> (num \<times> int) \<Rightarrow> fm" where
  5346   "stage p d \<equiv> (\<lambda> (e,c). evaldjf (\<lambda> j. simpfm (\<sigma> p c (Add e (C j)))) [1..c*d])"
  5347 lemma stage:
  5348   shows "Ifm bs (stage p d (e,c)) = (\<exists> j\<in>{1 .. c*d}. Ifm bs (\<sigma> p c (Add e (C j))))"
  5349   by (unfold stage_def split_def ,simp only: evaldjf_ex simpfm) simp
  5350 
  5351 lemma stage_nb: assumes lp: "iszlfm p (a#bs)" and cp: "c >0" and nb:"numbound0 e"
  5352   shows "bound0 (stage p d (e,c))"
  5353 proof-
  5354   let ?f = "\<lambda> j. simpfm (\<sigma> p c (Add e (C j)))"
  5355   have th: "\<forall> j\<in> set [1..c*d]. bound0 (?f j)"
  5356   proof
  5357     fix j
  5358     from nb have nb':"numbound0 (Add e (C j))" by simp
  5359     from simpfm_bound0[OF \<sigma>_nb[OF lp nb', where k="c"]]
  5360     show "bound0 (simpfm (\<sigma> p c (Add e (C j))))" .
  5361   qed
  5362   from evaldjf_bound0[OF th] show ?thesis by (unfold stage_def split_def) simp
  5363 qed
  5364 
  5365 definition redlove :: "fm \<Rightarrow> fm" where
  5366   "redlove p \<equiv> 
  5367   (let (q,B,d) = chooset p;
  5368        mq = simpfm (minusinf q);
  5369        md = evaldjf (\<lambda> j. simpfm (subst0 (C j) mq)) [1..d]
  5370    in if md = T then T else
  5371     (let qd = evaldjf (stage q d) B
  5372      in decr (disj md qd)))"
  5373 
  5374 lemma redlove: assumes qf: "qfree p"
  5375   shows "((\<exists> (x::int). Ifm (real x#bs) p) = (Ifm bs (redlove p))) \<and> qfree (redlove p)" 
  5376   (is "(?lhs = ?rhs) \<and> _")
  5377 proof-
  5378 
  5379   let ?I = "\<lambda> (x::int) p. Ifm (real x#bs) p"
  5380   let ?q = "fst (chooset p)"
  5381   let ?B = "fst (snd(chooset p))"
  5382   let ?d = "snd (snd (chooset p))"
  5383   let ?js = "[1..?d]"
  5384   let ?mq = "minusinf ?q"
  5385   let ?smq = "simpfm ?mq"
  5386   let ?md = "evaldjf (\<lambda> j. simpfm (subst0 (C j) ?smq)) ?js"
  5387   fix i
  5388   let ?N = "\<lambda> (t,k). (Inum (real (i::int)#bs) t,k)"
  5389   let ?qd = "evaldjf (stage ?q ?d) ?B"
  5390   have qbf:"chooset p = (?q,?B,?d)" by simp
  5391   from chooset[OF qf qbf] have pq_ex: "(\<exists>(x::int). ?I x p) = (\<exists> (x::int). ?I x ?q)" and 
  5392     B:"?N ` set ?B = ?N ` set (\<rho> ?q)" and dd: "\<delta> ?q = ?d" and dp: "?d > 0" and 
  5393     lq: "iszlfm ?q (real i#bs)" and 
  5394     Bn: "\<forall> (e,c)\<in> set ?B. numbound0 e \<and> c > 0" by auto
  5395   from zlin_qfree[OF lq] have qfq: "qfree ?q" .
  5396   from simpfm_qf[OF minusinf_qfree[OF qfq]] have qfmq: "qfree ?smq".
  5397   have jsnb: "\<forall> j \<in> set ?js. numbound0 (C j)" by simp
  5398   hence "\<forall> j\<in> set ?js. bound0 (subst0 (C j) ?smq)" 
  5399     by (auto simp only: subst0_bound0[OF qfmq])
  5400   hence th: "\<forall> j\<in> set ?js. bound0 (simpfm (subst0 (C j) ?smq))"
  5401     by (auto simp add: simpfm_bound0)
  5402   from evaldjf_bound0[OF th] have mdb: "bound0 ?md" by simp 
  5403   from Bn stage_nb[OF lq] have th:"\<forall> x \<in> set ?B. bound0 (stage ?q ?d x)" by auto
  5404   from evaldjf_bound0[OF th]  have qdb: "bound0 ?qd" .
  5405   from mdb qdb 
  5406   have mdqdb: "bound0 (disj ?md ?qd)" by (simp only: disj_def, cases "?md=T \<or> ?qd=T", simp_all)
  5407   from trans [OF pq_ex rl_thm'[OF lq B]] dd
  5408   have "?lhs = ((\<exists> j\<in> {1.. ?d}. ?I j ?mq) \<or> (\<exists> (e,c)\<in> set ?B. \<exists> j\<in> {1 .. c*?d}. Ifm (real i#bs) (\<sigma> ?q c (Add e (C j)))))" by auto
  5409   also have "\<dots> = ((\<exists> j\<in> {1.. ?d}. ?I j ?smq) \<or> (\<exists> (e,c)\<in> set ?B. ?I i (stage ?q ?d (e,c) )))" 
  5410     by (simp add: simpfm stage split_def)
  5411   also have "\<dots> = ((\<exists> j\<in> {1 .. ?d}. ?I i (subst0 (C j) ?smq))  \<or> ?I i ?qd)"
  5412     by (simp add: evaldjf_ex subst0_I[OF qfmq])
  5413   finally have mdqd:"?lhs = (?I i ?md \<or> ?I i ?qd)" by (simp only: evaldjf_ex set_upto simpfm) 
  5414   also have "\<dots> = (?I i (disj ?md ?qd))" by (simp add: disj)
  5415   also have "\<dots> = (Ifm bs (decr (disj ?md ?qd)))" by (simp only: decr [OF mdqdb]) 
  5416   finally have mdqd2: "?lhs = (Ifm bs (decr (disj ?md ?qd)))" . 
  5417   {assume mdT: "?md = T"
  5418     hence cT:"redlove p = T" by (simp add: redlove_def Let_def chooset_def split_def)
  5419     from mdT have lhs:"?lhs" using mdqd by simp 
  5420     from mdT have "?rhs" by (simp add: redlove_def chooset_def split_def)
  5421     with lhs cT have ?thesis by simp }
  5422   moreover
  5423   {assume mdT: "?md \<noteq> T" hence "redlove p = decr (disj ?md ?qd)" 
  5424       by (simp add: redlove_def chooset_def split_def Let_def)
  5425     with mdqd2 decr_qf[OF mdqdb] have ?thesis by simp }
  5426   ultimately show ?thesis by blast
  5427 qed
  5428 
  5429 lemma DJredlove: 
  5430   assumes qf: "qfree p"
  5431   shows "((\<exists> (x::int). Ifm (real x#bs) p) = (Ifm bs (DJ redlove p))) \<and> qfree (DJ redlove p)"
  5432 proof-
  5433   from redlove have cqf: "\<forall> p. qfree p \<longrightarrow> qfree (redlove p)" by  blast
  5434   from DJ_qf[OF cqf] qf have thqf:"qfree (DJ redlove p)" by blast
  5435   have "Ifm bs (DJ redlove p) = (\<exists> q\<in> set (disjuncts p). Ifm bs (redlove q))" 
  5436      by (simp add: DJ_def evaldjf_ex)
  5437   also have "\<dots> = (\<exists> q \<in> set(disjuncts p). \<exists> (x::int). Ifm (real x#bs)  q)" 
  5438     using redlove disjuncts_qf[OF qf] by blast
  5439   also have "\<dots> = (\<exists> (x::int). Ifm (real x#bs) p)" by (induct p rule: disjuncts.induct, auto)
  5440   finally show ?thesis using thqf by blast
  5441 qed
  5442 
  5443 
  5444 lemma exsplit_qf: assumes qf: "qfree p"
  5445   shows "qfree (exsplit p)"
  5446 using qf by (induct p rule: exsplit.induct, auto)
  5447 
  5448 definition mircfr :: "fm \<Rightarrow> fm" where
  5449   "mircfr = DJ cooper o ferrack01 o simpfm o exsplit"
  5450 
  5451 definition mirlfr :: "fm \<Rightarrow> fm" where
  5452   "mirlfr = DJ redlove o ferrack01 o simpfm o exsplit"
  5453 
  5454 lemma mircfr: "\<forall> bs p. qfree p \<longrightarrow> qfree (mircfr p) \<and> Ifm bs (mircfr p) = Ifm bs (E p)"
  5455 proof(clarsimp simp del: Ifm.simps)
  5456   fix bs p
  5457   assume qf: "qfree p"
  5458   show "qfree (mircfr p)\<and>(Ifm bs (mircfr p) = Ifm bs (E p))" (is "_ \<and> (?lhs = ?rhs)")
  5459   proof-
  5460     let ?es = "(And (And (Ge (CN 0 1 (C 0))) (Lt (CN 0 1 (C (- 1))))) (simpfm (exsplit p)))"
  5461     have "?rhs = (\<exists> (i::int). \<exists> x. Ifm (x#real i#bs) ?es)" 
  5462       using splitex[OF qf] by simp
  5463     with ferrack01[OF simpfm_qf[OF exsplit_qf[OF qf]]] have th1: "?rhs = (\<exists> (i::int). Ifm (real i#bs) (ferrack01 (simpfm (exsplit p))))" and qf':"qfree (ferrack01 (simpfm (exsplit p)))" by simp+
  5464     with DJcooper[OF qf'] show ?thesis by (simp add: mircfr_def)
  5465   qed
  5466 qed
  5467   
  5468 lemma mirlfr: "\<forall> bs p. qfree p \<longrightarrow> qfree(mirlfr p) \<and> Ifm bs (mirlfr p) = Ifm bs (E p)"
  5469 proof(clarsimp simp del: Ifm.simps)
  5470   fix bs p
  5471   assume qf: "qfree p"
  5472   show "qfree (mirlfr p)\<and>(Ifm bs (mirlfr p) = Ifm bs (E p))" (is "_ \<and> (?lhs = ?rhs)")
  5473   proof-
  5474     let ?es = "(And (And (Ge (CN 0 1 (C 0))) (Lt (CN 0 1 (C (- 1))))) (simpfm (exsplit p)))"
  5475     have "?rhs = (\<exists> (i::int). \<exists> x. Ifm (x#real i#bs) ?es)" 
  5476       using splitex[OF qf] by simp
  5477     with ferrack01[OF simpfm_qf[OF exsplit_qf[OF qf]]] have th1: "?rhs = (\<exists> (i::int). Ifm (real i#bs) (ferrack01 (simpfm (exsplit p))))" and qf':"qfree (ferrack01 (simpfm (exsplit p)))" by simp+
  5478     with DJredlove[OF qf'] show ?thesis by (simp add: mirlfr_def)
  5479   qed
  5480 qed
  5481   
  5482 definition mircfrqe:: "fm \<Rightarrow> fm" where
  5483   "mircfrqe p = qelim (prep p) mircfr"
  5484 
  5485 definition mirlfrqe:: "fm \<Rightarrow> fm" where
  5486   "mirlfrqe p = qelim (prep p) mirlfr"
  5487 
  5488 theorem mircfrqe: "(Ifm bs (mircfrqe p) = Ifm bs p) \<and> qfree (mircfrqe p)"
  5489   using qelim_ci[OF mircfr] prep by (auto simp add: mircfrqe_def)
  5490 
  5491 theorem mirlfrqe: "(Ifm bs (mirlfrqe p) = Ifm bs p) \<and> qfree (mirlfrqe p)"
  5492   using qelim_ci[OF mirlfr] prep by (auto simp add: mirlfrqe_def)
  5493 
  5494 definition
  5495   "problem1 = A (And (Le (Sub (Floor (Bound 0)) (Bound 0))) (Le (Add (Bound 0) (Floor (Neg (Bound 0))))))"
  5496 
  5497 definition
  5498   "problem2 = A (Iff (Eq (Add (Floor (Bound 0)) (Floor (Neg (Bound 0))))) (Eq (Sub (Floor (Bound 0)) (Bound 0))))"
  5499 
  5500 definition
  5501   "problem3 = A (And (Le (Sub (Floor (Bound 0)) (Bound 0))) (Le (Add (Bound 0) (Floor (Neg (Bound 0))))))"
  5502 
  5503 definition
  5504   "problem4 = E (And (Ge (Sub (Bound 1) (Bound 0))) (Eq (Add (Floor (Bound 1)) (Floor (Neg (Bound 0))))))"
  5505 
  5506 ML {* @{code mircfrqe} @{code problem1} *}
  5507 ML {* @{code mirlfrqe} @{code problem1} *}  
  5508 ML {* @{code mircfrqe} @{code problem2} *}
  5509 ML {* @{code mirlfrqe} @{code problem2} *}  
  5510 ML {* @{code mircfrqe} @{code problem3} *}
  5511 ML {* @{code mirlfrqe} @{code problem3} *}  
  5512 ML {* @{code mircfrqe} @{code problem4} *}
  5513 ML {* @{code mirlfrqe} @{code problem4} *}
  5514 
  5515 (*code_reflect Mir
  5516   functions mircfrqe mirlfrqe
  5517   file "mir.ML"*)
  5518 
  5519 oracle mirfr_oracle = {* fn (proofs, ct) =>
  5520 let
  5521 
  5522 fun num_of_term vs (t as Free (xn, xT)) = (case AList.lookup (op =) vs t
  5523      of NONE => error "Variable not found in the list!"
  5524       | SOME n => @{code Bound} n)
  5525   | num_of_term vs @{term "real (0::int)"} = @{code C} 0
  5526   | num_of_term vs @{term "real (1::int)"} = @{code C} 1
  5527   | num_of_term vs @{term "0::real"} = @{code C} 0
  5528   | num_of_term vs @{term "1::real"} = @{code C} 1
  5529   | num_of_term vs (Bound i) = @{code Bound} i
  5530   | num_of_term vs (@{term "uminus :: real \<Rightarrow> real"} $ t') = @{code Neg} (num_of_term vs t')
  5531   | num_of_term vs (@{term "op + :: real \<Rightarrow> real \<Rightarrow> real"} $ t1 $ t2) =
  5532       @{code Add} (num_of_term vs t1, num_of_term vs t2)
  5533   | num_of_term vs (@{term "op - :: real \<Rightarrow> real \<Rightarrow> real"} $ t1 $ t2) =
  5534       @{code Sub} (num_of_term vs t1, num_of_term vs t2)
  5535   | num_of_term vs (@{term "op * :: real \<Rightarrow> real \<Rightarrow> real"} $ t1 $ t2) =
  5536       (case (num_of_term vs t1)
  5537        of @{code C} i => @{code Mul} (i, num_of_term vs t2)
  5538         | _ => error "num_of_term: unsupported Multiplication")
  5539   | num_of_term vs (@{term "real :: int \<Rightarrow> real"} $ (@{term "numeral :: _ \<Rightarrow> int"} $ t')) =
  5540       @{code C} (HOLogic.dest_num t')
  5541   | num_of_term vs (@{term "real :: int \<Rightarrow> real"} $ (@{term "neg_numeral :: _ \<Rightarrow> int"} $ t')) =
  5542       @{code C} (~ (HOLogic.dest_num t'))
  5543   | num_of_term vs (@{term "real :: int \<Rightarrow> real"} $ (@{term "floor :: real \<Rightarrow> int"} $ t')) =
  5544       @{code Floor} (num_of_term vs t')
  5545   | num_of_term vs (@{term "real :: int \<Rightarrow> real"} $ (@{term "ceiling :: real \<Rightarrow> int"} $ t')) =
  5546       @{code Neg} (@{code Floor} (@{code Neg} (num_of_term vs t')))
  5547   | num_of_term vs (@{term "numeral :: _ \<Rightarrow> real"} $ t') =
  5548       @{code C} (HOLogic.dest_num t')
  5549   | num_of_term vs (@{term "neg_numeral :: _ \<Rightarrow> real"} $ t') =
  5550       @{code C} (~ (HOLogic.dest_num t'))
  5551   | num_of_term vs t = error ("num_of_term: unknown term " ^ Syntax.string_of_term @{context} t);
  5552 
  5553 fun fm_of_term vs @{term True} = @{code T}
  5554   | fm_of_term vs @{term False} = @{code F}
  5555   | fm_of_term vs (@{term "op < :: real \<Rightarrow> real \<Rightarrow> bool"} $ t1 $ t2) =
  5556       @{code Lt} (@{code Sub} (num_of_term vs t1, num_of_term vs t2))
  5557   | fm_of_term vs (@{term "op \<le> :: real \<Rightarrow> real \<Rightarrow> bool"} $ t1 $ t2) =
  5558       @{code Le} (@{code Sub} (num_of_term vs t1, num_of_term vs t2))
  5559   | fm_of_term vs (@{term "op = :: real \<Rightarrow> real \<Rightarrow> bool"} $ t1 $ t2) =
  5560       @{code Eq} (@{code S