src/HOL/Complex/ex/MIR.thy
changeset 25765 49580bd58a21
parent 25162 ad4d5365d9d8
child 26932 c398a3866082
equal deleted inserted replaced
25764:878c37886eed 25765:49580bd58a21
     9   uses ("mireif.ML") ("mirtac.ML")
     9   uses ("mireif.ML") ("mirtac.ML")
    10   begin
    10   begin
    11 
    11 
    12 declare real_of_int_floor_cancel [simp del]
    12 declare real_of_int_floor_cancel [simp del]
    13 
    13 
    14 fun alluopairs:: "'a list \<Rightarrow> ('a \<times> 'a) list" where 
    14 primrec alluopairs:: "'a list \<Rightarrow> ('a \<times> 'a) list" where 
    15   "alluopairs [] = []"
    15   "alluopairs [] = []"
    16 | "alluopairs (x#xs) = (map (Pair x) (x#xs))@(alluopairs xs)"
    16 | "alluopairs (x#xs) = (map (Pair x) (x#xs))@(alluopairs xs)"
    17 
    17 
    18 lemma alluopairs_set1: "set (alluopairs xs) \<le> {(x,y). x\<in> set xs \<and> y\<in> set xs}"
    18 lemma alluopairs_set1: "set (alluopairs xs) \<le> {(x,y). x\<in> set xs \<and> y\<in> set xs}"
    19 by (induct xs, auto)
    19 by (induct xs, auto)
   171 
   171 
   172 datatype num = C int | Bound nat | CN nat int num | Neg num | Add num num| Sub num num 
   172 datatype num = C int | Bound nat | CN nat int num | Neg num | Add num num| Sub num num 
   173   | Mul int num | Floor num| CF int num num
   173   | Mul int num | Floor num| CF int num num
   174 
   174 
   175   (* A size for num to make inductive proofs simpler*)
   175   (* A size for num to make inductive proofs simpler*)
   176 fun num_size :: "num \<Rightarrow> nat" where
   176 primrec num_size :: "num \<Rightarrow> nat" where
   177  "num_size (C c) = 1"
   177  "num_size (C c) = 1"
   178 | "num_size (Bound n) = 1"
   178 | "num_size (Bound n) = 1"
   179 | "num_size (Neg a) = 1 + num_size a"
   179 | "num_size (Neg a) = 1 + num_size a"
   180 | "num_size (Add a b) = 1 + num_size a + num_size b"
   180 | "num_size (Add a b) = 1 + num_size a + num_size b"
   181 | "num_size (Sub a b) = 3 + num_size a + num_size b"
   181 | "num_size (Sub a b) = 3 + num_size a + num_size b"
   183 | "num_size (CF c a b) = 4 + num_size a + num_size b"
   183 | "num_size (CF c a b) = 4 + num_size a + num_size b"
   184 | "num_size (Mul c a) = 1 + num_size a"
   184 | "num_size (Mul c a) = 1 + num_size a"
   185 | "num_size (Floor a) = 1 + num_size a"
   185 | "num_size (Floor a) = 1 + num_size a"
   186 
   186 
   187   (* Semantics of numeral terms (num) *)
   187   (* Semantics of numeral terms (num) *)
   188 fun Inum :: "real list \<Rightarrow> num \<Rightarrow> real" where
   188 primrec Inum :: "real list \<Rightarrow> num \<Rightarrow> real" where
   189   "Inum bs (C c) = (real c)"
   189   "Inum bs (C c) = (real c)"
   190 | "Inum bs (Bound n) = bs!n"
   190 | "Inum bs (Bound n) = bs!n"
   191 | "Inum bs (CN n c a) = (real c) * (bs!n) + (Inum bs a)"
   191 | "Inum bs (CN n c a) = (real c) * (bs!n) + (Inum bs a)"
   192 | "Inum bs (Neg a) = -(Inum bs a)"
   192 | "Inum bs (Neg a) = -(Inum bs a)"
   193 | "Inum bs (Add a b) = Inum bs a + Inum bs b"
   193 | "Inum bs (Add a b) = Inum bs a + Inum bs b"
   270   (* several lemmas about fmsize *)
   270   (* several lemmas about fmsize *)
   271 lemma fmsize_pos: "fmsize p > 0"	
   271 lemma fmsize_pos: "fmsize p > 0"	
   272 by (induct p rule: fmsize.induct) simp_all
   272 by (induct p rule: fmsize.induct) simp_all
   273 
   273 
   274   (* Semantics of formulae (fm) *)
   274   (* Semantics of formulae (fm) *)
   275 fun Ifm ::"real list \<Rightarrow> fm \<Rightarrow> bool" where
   275 primrec Ifm ::"real list \<Rightarrow> fm \<Rightarrow> bool" where
   276   "Ifm bs T = True"
   276   "Ifm bs T = True"
   277 | "Ifm bs F = False"
   277 | "Ifm bs F = False"
   278 | "Ifm bs (Lt a) = (Inum bs a < 0)"
   278 | "Ifm bs (Lt a) = (Inum bs a < 0)"
   279 | "Ifm bs (Gt a) = (Inum bs a > 0)"
   279 | "Ifm bs (Gt a) = (Inum bs a > 0)"
   280 | "Ifm bs (Le a) = (Inum bs a \<le> 0)"
   280 | "Ifm bs (Le a) = (Inum bs a \<le> 0)"
   320 lemma prep: "\<And> bs. Ifm bs (prep p) = Ifm bs p"
   320 lemma prep: "\<And> bs. Ifm bs (prep p) = Ifm bs p"
   321 by (induct p rule: prep.induct, auto)
   321 by (induct p rule: prep.induct, auto)
   322 
   322 
   323 
   323 
   324   (* Quantifier freeness *)
   324   (* Quantifier freeness *)
   325 consts qfree:: "fm \<Rightarrow> bool"
   325 fun qfree:: "fm \<Rightarrow> bool" where
   326 recdef qfree "measure size"
       
   327   "qfree (E p) = False"
   326   "qfree (E p) = False"
   328   "qfree (A p) = False"
   327   | "qfree (A p) = False"
   329   "qfree (NOT p) = qfree p" 
   328   | "qfree (NOT p) = qfree p" 
   330   "qfree (And p q) = (qfree p \<and> qfree q)" 
   329   | "qfree (And p q) = (qfree p \<and> qfree q)" 
   331   "qfree (Or  p q) = (qfree p \<and> qfree q)" 
   330   | "qfree (Or  p q) = (qfree p \<and> qfree q)" 
   332   "qfree (Imp p q) = (qfree p \<and> qfree q)" 
   331   | "qfree (Imp p q) = (qfree p \<and> qfree q)" 
   333   "qfree (Iff p q) = (qfree p \<and> qfree q)"
   332   | "qfree (Iff p q) = (qfree p \<and> qfree q)"
   334   "qfree p = True"
   333   | "qfree p = True"
   335 
   334 
   336   (* Boundedness and substitution *)
   335   (* Boundedness and substitution *)
   337 consts 
   336 primrec numbound0 :: "num \<Rightarrow> bool" (* a num is INDEPENDENT of Bound 0 *) where
   338   numbound0:: "num \<Rightarrow> bool" (* a num is INDEPENDENT of Bound 0 *)
       
   339   bound0:: "fm \<Rightarrow> bool" (* A Formula is independent of Bound 0 *)
       
   340   numsubst0:: "num \<Rightarrow> num \<Rightarrow> num" (* substitute a num into a num for Bound 0 *)
       
   341   subst0:: "num \<Rightarrow> fm \<Rightarrow> fm" (* substitue a num into a formula for Bound 0 *)
       
   342 primrec
       
   343   "numbound0 (C c) = True"
   337   "numbound0 (C c) = True"
   344   "numbound0 (Bound n) = (n>0)"
   338   | "numbound0 (Bound n) = (n>0)"
   345   "numbound0 (CN n i a) = (n > 0 \<and> numbound0 a)"
   339   | "numbound0 (CN n i a) = (n > 0 \<and> numbound0 a)"
   346   "numbound0 (Neg a) = numbound0 a"
   340   | "numbound0 (Neg a) = numbound0 a"
   347   "numbound0 (Add a b) = (numbound0 a \<and> numbound0 b)"
   341   | "numbound0 (Add a b) = (numbound0 a \<and> numbound0 b)"
   348   "numbound0 (Sub a b) = (numbound0 a \<and> numbound0 b)" 
   342   | "numbound0 (Sub a b) = (numbound0 a \<and> numbound0 b)" 
   349   "numbound0 (Mul i a) = numbound0 a"
   343   | "numbound0 (Mul i a) = numbound0 a"
   350   "numbound0 (Floor a) = numbound0 a"
   344   | "numbound0 (Floor a) = numbound0 a"
   351   "numbound0 (CF c a b) = (numbound0 a \<and> numbound0 b)" 
   345   | "numbound0 (CF c a b) = (numbound0 a \<and> numbound0 b)" 
       
   346 
   352 lemma numbound0_I:
   347 lemma numbound0_I:
   353   assumes nb: "numbound0 a"
   348   assumes nb: "numbound0 a"
   354   shows "Inum (b#bs) a = Inum (b'#bs) a"
   349   shows "Inum (b#bs) a = Inum (b'#bs) a"
   355 using nb
   350   using nb by (induct a) (auto simp add: nth_pos2)
   356 by (induct a rule: numbound0.induct) (auto simp add: nth_pos2)
       
   357 
       
   358 
   351 
   359 lemma numbound0_gen: 
   352 lemma numbound0_gen: 
   360   assumes nb: "numbound0 t" and ti: "isint t (x#bs)"
   353   assumes nb: "numbound0 t" and ti: "isint t (x#bs)"
   361   shows "\<forall> y. isint t (y#bs)"
   354   shows "\<forall> y. isint t (y#bs)"
   362 using nb ti 
   355 using nb ti 
   365   from numbound0_I[OF nb, where bs="bs" and b="y" and b'="x"] ti[simplified isint_def]
   358   from numbound0_I[OF nb, where bs="bs" and b="y" and b'="x"] ti[simplified isint_def]
   366   show "isint t (y#bs)"
   359   show "isint t (y#bs)"
   367     by (simp add: isint_def)
   360     by (simp add: isint_def)
   368 qed
   361 qed
   369 
   362 
   370 primrec
   363 primrec bound0:: "fm \<Rightarrow> bool" (* A Formula is independent of Bound 0 *) where
   371   "bound0 T = True"
   364   "bound0 T = True"
   372   "bound0 F = True"
   365   | "bound0 F = True"
   373   "bound0 (Lt a) = numbound0 a"
   366   | "bound0 (Lt a) = numbound0 a"
   374   "bound0 (Le a) = numbound0 a"
   367   | "bound0 (Le a) = numbound0 a"
   375   "bound0 (Gt a) = numbound0 a"
   368   | "bound0 (Gt a) = numbound0 a"
   376   "bound0 (Ge a) = numbound0 a"
   369   | "bound0 (Ge a) = numbound0 a"
   377   "bound0 (Eq a) = numbound0 a"
   370   | "bound0 (Eq a) = numbound0 a"
   378   "bound0 (NEq a) = numbound0 a"
   371   | "bound0 (NEq a) = numbound0 a"
   379   "bound0 (Dvd i a) = numbound0 a"
   372   | "bound0 (Dvd i a) = numbound0 a"
   380   "bound0 (NDvd i a) = numbound0 a"
   373   | "bound0 (NDvd i a) = numbound0 a"
   381   "bound0 (NOT p) = bound0 p"
   374   | "bound0 (NOT p) = bound0 p"
   382   "bound0 (And p q) = (bound0 p \<and> bound0 q)"
   375   | "bound0 (And p q) = (bound0 p \<and> bound0 q)"
   383   "bound0 (Or p q) = (bound0 p \<and> bound0 q)"
   376   | "bound0 (Or p q) = (bound0 p \<and> bound0 q)"
   384   "bound0 (Imp p q) = ((bound0 p) \<and> (bound0 q))"
   377   | "bound0 (Imp p q) = ((bound0 p) \<and> (bound0 q))"
   385   "bound0 (Iff p q) = (bound0 p \<and> bound0 q)"
   378   | "bound0 (Iff p q) = (bound0 p \<and> bound0 q)"
   386   "bound0 (E p) = False"
   379   | "bound0 (E p) = False"
   387   "bound0 (A p) = False"
   380   | "bound0 (A p) = False"
   388 
   381 
   389 lemma bound0_I:
   382 lemma bound0_I:
   390   assumes bp: "bound0 p"
   383   assumes bp: "bound0 p"
   391   shows "Ifm (b#bs) p = Ifm (b'#bs) p"
   384   shows "Ifm (b#bs) p = Ifm (b'#bs) p"
   392 using bp numbound0_I[where b="b" and bs="bs" and b'="b'"]
   385  using bp numbound0_I [where b="b" and bs="bs" and b'="b'"]
   393 by (induct p rule: bound0.induct) (auto simp add: nth_pos2)
   386   by (induct p) (auto simp add: nth_pos2)
   394 
   387 
   395 primrec
   388 primrec numsubst0:: "num \<Rightarrow> num \<Rightarrow> num" (* substitute a num into a num for Bound 0 *) where
   396   "numsubst0 t (C c) = (C c)"
   389   "numsubst0 t (C c) = (C c)"
   397   "numsubst0 t (Bound n) = (if n=0 then t else Bound n)"
   390   | "numsubst0 t (Bound n) = (if n=0 then t else Bound n)"
   398   "numsubst0 t (CN n i a) = (if n=0 then Add (Mul i t) (numsubst0 t a) else CN n i (numsubst0 t a))"
   391   | "numsubst0 t (CN n i a) = (if n=0 then Add (Mul i t) (numsubst0 t a) else CN n i (numsubst0 t a))"
   399   "numsubst0 t (CF i a b) = CF i (numsubst0 t a) (numsubst0 t b)"
   392   | "numsubst0 t (CF i a b) = CF i (numsubst0 t a) (numsubst0 t b)"
   400   "numsubst0 t (Neg a) = Neg (numsubst0 t a)"
   393   | "numsubst0 t (Neg a) = Neg (numsubst0 t a)"
   401   "numsubst0 t (Add a b) = Add (numsubst0 t a) (numsubst0 t b)"
   394   | "numsubst0 t (Add a b) = Add (numsubst0 t a) (numsubst0 t b)"
   402   "numsubst0 t (Sub a b) = Sub (numsubst0 t a) (numsubst0 t b)" 
   395   | "numsubst0 t (Sub a b) = Sub (numsubst0 t a) (numsubst0 t b)" 
   403   "numsubst0 t (Mul i a) = Mul i (numsubst0 t a)"
   396   | "numsubst0 t (Mul i a) = Mul i (numsubst0 t a)"
   404   "numsubst0 t (Floor a) = Floor (numsubst0 t a)"
   397   | "numsubst0 t (Floor a) = Floor (numsubst0 t a)"
   405 
   398 
   406 lemma numsubst0_I:
   399 lemma numsubst0_I:
   407   shows "Inum (b#bs) (numsubst0 a t) = Inum ((Inum (b#bs) a)#bs) t"
   400   shows "Inum (b#bs) (numsubst0 a t) = Inum ((Inum (b#bs) a)#bs) t"
   408   by (induct t) (simp_all add: nth_pos2)
   401   by (induct t) (simp_all add: nth_pos2)
   409 
   402 
   410 lemma numsubst0_I':
   403 lemma numsubst0_I':
   411   assumes nb: "numbound0 a"
   404   assumes nb: "numbound0 a"
   412   shows "Inum (b#bs) (numsubst0 a t) = Inum ((Inum (b'#bs) a)#bs) t"
   405   shows "Inum (b#bs) (numsubst0 a t) = Inum ((Inum (b'#bs) a)#bs) t"
   413   by (induct t) (simp_all add: nth_pos2 numbound0_I[OF nb, where b="b" and b'="b'"])
   406   by (induct t) (simp_all add: nth_pos2 numbound0_I[OF nb, where b="b" and b'="b'"])
   414 
   407 
   415 
   408 primrec subst0:: "num \<Rightarrow> fm \<Rightarrow> fm" (* substitue a num into a formula for Bound 0 *) where
   416 primrec
       
   417   "subst0 t T = T"
   409   "subst0 t T = T"
   418   "subst0 t F = F"
   410   | "subst0 t F = F"
   419   "subst0 t (Lt a) = Lt (numsubst0 t a)"
   411   | "subst0 t (Lt a) = Lt (numsubst0 t a)"
   420   "subst0 t (Le a) = Le (numsubst0 t a)"
   412   | "subst0 t (Le a) = Le (numsubst0 t a)"
   421   "subst0 t (Gt a) = Gt (numsubst0 t a)"
   413   | "subst0 t (Gt a) = Gt (numsubst0 t a)"
   422   "subst0 t (Ge a) = Ge (numsubst0 t a)"
   414   | "subst0 t (Ge a) = Ge (numsubst0 t a)"
   423   "subst0 t (Eq a) = Eq (numsubst0 t a)"
   415   | "subst0 t (Eq a) = Eq (numsubst0 t a)"
   424   "subst0 t (NEq a) = NEq (numsubst0 t a)"
   416   | "subst0 t (NEq a) = NEq (numsubst0 t a)"
   425   "subst0 t (Dvd i a) = Dvd i (numsubst0 t a)"
   417   | "subst0 t (Dvd i a) = Dvd i (numsubst0 t a)"
   426   "subst0 t (NDvd i a) = NDvd i (numsubst0 t a)"
   418   | "subst0 t (NDvd i a) = NDvd i (numsubst0 t a)"
   427   "subst0 t (NOT p) = NOT (subst0 t p)"
   419   | "subst0 t (NOT p) = NOT (subst0 t p)"
   428   "subst0 t (And p q) = And (subst0 t p) (subst0 t q)"
   420   | "subst0 t (And p q) = And (subst0 t p) (subst0 t q)"
   429   "subst0 t (Or p q) = Or (subst0 t p) (subst0 t q)"
   421   | "subst0 t (Or p q) = Or (subst0 t p) (subst0 t q)"
   430   "subst0 t (Imp p q) = Imp (subst0 t p) (subst0 t q)"
   422   | "subst0 t (Imp p q) = Imp (subst0 t p) (subst0 t q)"
   431   "subst0 t (Iff p q) = Iff (subst0 t p) (subst0 t q)"
   423   | "subst0 t (Iff p q) = Iff (subst0 t p) (subst0 t q)"
   432 
   424 
   433 lemma subst0_I: assumes qfp: "qfree p"
   425 lemma subst0_I: assumes qfp: "qfree p"
   434   shows "Ifm (b#bs) (subst0 a p) = Ifm ((Inum (b#bs) a)#bs) p"
   426   shows "Ifm (b#bs) (subst0 a p) = Ifm ((Inum (b#bs) a)#bs) p"
   435   using qfp numsubst0_I[where b="b" and bs="bs" and a="a"]
   427   using qfp numsubst0_I[where b="b" and bs="bs" and a="a"]
   436   by (induct p) (simp_all add: nth_pos2 )
   428   by (induct p) (simp_all add: nth_pos2 )
   437 
   429 
   438 consts 
   430 consts
   439   decrnum:: "num \<Rightarrow> num" 
   431   decrnum:: "num \<Rightarrow> num" 
   440   decr :: "fm \<Rightarrow> fm"
   432   decr :: "fm \<Rightarrow> fm"
   441 
   433 
   442 recdef decrnum "measure size"
   434 recdef decrnum "measure size"
   443   "decrnum (Bound n) = Bound (n - 1)"
   435   "decrnum (Bound n) = Bound (n - 1)"
   493   "isatom (NDvd i b) = True"
   485   "isatom (NDvd i b) = True"
   494   "isatom p = False"
   486   "isatom p = False"
   495 
   487 
   496 lemma numsubst0_numbound0: assumes nb: "numbound0 t"
   488 lemma numsubst0_numbound0: assumes nb: "numbound0 t"
   497   shows "numbound0 (numsubst0 t a)"
   489   shows "numbound0 (numsubst0 t a)"
   498 using nb by (induct a rule: numsubst0.induct, auto)
   490 using nb by (induct a, auto)
   499 
   491 
   500 lemma subst0_bound0: assumes qf: "qfree p" and nb: "numbound0 t"
   492 lemma subst0_bound0: assumes qf: "qfree p" and nb: "numbound0 t"
   501   shows "bound0 (subst0 t p)"
   493   shows "bound0 (subst0 t p)"
   502 using qf numsubst0_numbound0[OF nb] by (induct p  rule: subst0.induct, auto)
   494 using qf numsubst0_numbound0[OF nb] by (induct p, auto)
   503 
   495 
   504 lemma bound0_qf: "bound0 p \<Longrightarrow> qfree p"
   496 lemma bound0_qf: "bound0 p \<Longrightarrow> qfree p"
   505 by (induct p, simp_all)
   497 by (induct p, simp_all)
   506 
   498 
   507 
   499 
   508 constdefs djf:: "('a \<Rightarrow> fm) \<Rightarrow> 'a \<Rightarrow> fm \<Rightarrow> fm"
   500 definition djf:: "('a \<Rightarrow> fm) \<Rightarrow> 'a \<Rightarrow> fm \<Rightarrow> fm" where
   509   "djf f p q \<equiv> (if q=T then T else if q=F then f p else 
   501   "djf f p q = (if q=T then T else if q=F then f p else 
   510   (let fp = f p in case fp of T \<Rightarrow> T | F \<Rightarrow> q | _ \<Rightarrow> Or fp q))"
   502   (let fp = f p in case fp of T \<Rightarrow> T | F \<Rightarrow> q | _ \<Rightarrow> Or fp q))"
   511 constdefs evaldjf:: "('a \<Rightarrow> fm) \<Rightarrow> 'a list \<Rightarrow> fm"
   503 
   512   "evaldjf f ps \<equiv> foldr (djf f) ps F"
   504 definition evaldjf:: "('a \<Rightarrow> fm) \<Rightarrow> 'a list \<Rightarrow> fm" where
       
   505   "evaldjf f ps = foldr (djf f) ps F"
   513 
   506 
   514 lemma djf_Or: "Ifm bs (djf f p q) = Ifm bs (Or (f p) q)"
   507 lemma djf_Or: "Ifm bs (djf f p q) = Ifm bs (Or (f p) q)"
   515 by (cases "q=T", simp add: djf_def,cases "q=F",simp add: djf_def) 
   508 by (cases "q=T", simp add: djf_def,cases "q=F",simp add: djf_def) 
   516 (cases "f p", simp_all add: Let_def djf_def) 
   509 (cases "f p", simp_all add: Let_def djf_def) 
   517 
   510