[3] | 1 | (**************************************************************************) |
---|
| 2 | (* ___ *) |
---|
| 3 | (* ||M|| *) |
---|
| 4 | (* ||A|| A project by Andrea Asperti *) |
---|
| 5 | (* ||T|| *) |
---|
| 6 | (* ||I|| Developers: *) |
---|
| 7 | (* ||T|| The HELM team. *) |
---|
| 8 | (* ||A|| http://helm.cs.unibo.it *) |
---|
| 9 | (* \ / *) |
---|
| 10 | (* \ / This file is distributed under the terms of the *) |
---|
| 11 | (* v GNU General Public License Version 2 *) |
---|
| 12 | (* *) |
---|
| 13 | (**************************************************************************) |
---|
| 14 | |
---|
[487] | 15 | include "basics/types.ma". |
---|
[1599] | 16 | include "basics/lists/list.ma". |
---|
[487] | 17 | include "basics/logic.ma". |
---|
[1593] | 18 | include "ASM/Util.ma". |
---|
[3] | 19 | |
---|
[487] | 20 | lemma eq_rect_Type0_r: |
---|
[3] | 21 | ∀A.∀a.∀P: ∀x:A. eq ? x a → Type[0]. P a (refl A a) → ∀x.∀p:eq ? x a.P x p. |
---|
[487] | 22 | #A #a #P #p #x0 #p0 @(eq_rect_r ??? p0) assumption. |
---|
| 23 | qed. |
---|
[3] | 24 | |
---|
[487] | 25 | lemma eq_rect_r2: |
---|
[3] | 26 | ∀A.∀a,x.∀p:eq ? x a.∀P: ∀x:A. eq ? x a → Type[2]. P a (refl A a) → P x p. |
---|
[487] | 27 | #A #a #x #p cases p; #P #H assumption. |
---|
| 28 | qed. |
---|
[3] | 29 | |
---|
[487] | 30 | lemma eq_rect_Type2_r: |
---|
[3] | 31 | ∀A.∀a.∀P: ∀x:A. eq ? x a → Type[2]. P a (refl A a) → ∀x.∀p:eq ? x a.P x p. |
---|
[487] | 32 | #A #a #P #p #x0 #p0 @(eq_rect_r2 ??? p0) assumption. |
---|
| 33 | qed. |
---|
[3] | 34 | |
---|
[487] | 35 | lemma eq_rect_CProp0_r: |
---|
[16] | 36 | ∀A.∀a.∀P: ∀x:A. eq ? x a → CProp[0]. P a (refl A a) → ∀x.∀p:eq ? x a.P x p. |
---|
[487] | 37 | #A #a #P #p #x0 #p0 @(eq_rect_r2 ??? p0) assumption. |
---|
| 38 | qed. |
---|
[16] | 39 | |
---|
[487] | 40 | lemma sym_neq : ∀A.∀x,y:A. x ≠ y → y ≠ x. |
---|
| 41 | #A #x #y *;#H @nmk #H' /2/; |
---|
| 42 | qed. |
---|
[3] | 43 | |
---|
| 44 | interpretation "logical iff" 'iff x y = (iff x y). |
---|
| 45 | |
---|
| 46 | (* bool *) |
---|
| 47 | |
---|
[487] | 48 | definition xorb : bool → bool → bool ≝ |
---|
[3] | 49 | λx,y. match x with [ false ⇒ y | true ⇒ notb y ]. |
---|
| 50 | |
---|
[1523] | 51 | |
---|
| 52 | |
---|
[3] | 53 | |
---|
| 54 | (* should be proved in nat.ma, but it's not! *) |
---|
[1882] | 55 | (* Paolo: there is eqb_elim which does something very similar *) |
---|
[487] | 56 | lemma eqb_to_Prop : ∀n,m:nat.match eqb n m with [ true ⇒ n = m | false ⇒ n ≠ m ]. |
---|
| 57 | #n elim n; |
---|
| 58 | [ #m cases m; //; |
---|
| 59 | | #n' #IH #m cases m; [ /2/; | #m' whd in match (eqb (S n') (S m')) in ⊢ %; |
---|
| 60 | lapply (IH m'); cases (eqb n' m'); /2/; ] |
---|
| 61 | ] qed. |
---|
[3] | 62 | |
---|
| 63 | (* datatypes/list.ma *) |
---|
| 64 | |
---|
[487] | 65 | theorem nil_append_nil_both: |
---|
| 66 | ∀A:Type[0]. ∀l1,l2:list A. |
---|
[3] | 67 | l1 @ l2 = [] → l1 = [] ∧ l2 = []. |
---|
[891] | 68 | #A #l1 #l2 cases l1 |
---|
| 69 | [ cases l2 |
---|
[487] | 70 | [ /2/ |
---|
[891] | 71 | | normalize #h #t #H destruct |
---|
[487] | 72 | ] |
---|
[891] | 73 | | cases l2 |
---|
| 74 | [ normalize #h #t #H destruct |
---|
| 75 | | normalize #h1 #t1 #h2 #h3 #H destruct |
---|
[487] | 76 | ] |
---|
| 77 | ] qed. |
---|
[1593] | 78 | |
---|
| 79 | (* some useful stuff for quantifiers *) |
---|
| 80 | |
---|
| 81 | lemma dec_bounded_forall: |
---|
| 82 | ∀P:ℕ → Prop.(∀n.(P n) + (¬P n)) → ∀k.(∀n.n < k → P n) + ¬(∀n.n < k → P n). |
---|
| 83 | #P #HP_dec #k elim k -k |
---|
| 84 | [ %1 #n #Hn @⊥ @(absurd (n < 0) Hn) @not_le_Sn_O |
---|
| 85 | | #k #Hind cases Hind |
---|
| 86 | [ #Hk cases (HP_dec k) |
---|
| 87 | [ #HPk %1 #n #Hn cases (le_to_or_lt_eq … Hn) |
---|
| 88 | [ #H @(Hk … (le_S_S_to_le … H)) |
---|
| 89 | | #H >(injective_S … H) @HPk |
---|
| 90 | ] |
---|
| 91 | | #HPk %2 @nmk #Habs @(absurd (P k)) [ @(Habs … (le_n (S k))) | @HPk ] |
---|
| 92 | ] |
---|
| 93 | | #Hk %2 @nmk #Habs @(absurd (∀n.n<k→P n)) [ #n' #Hn' @(Habs … (le_S … Hn')) | @Hk ] |
---|
| 94 | ] |
---|
| 95 | ] |
---|
| 96 | qed. |
---|
| 97 | |
---|
| 98 | lemma dec_bounded_exists: |
---|
| 99 | ∀P:ℕ→Prop.(∀n.(P n) + (¬P n)) → ∀k.(∃n.n < k ∧ P n) + ¬(∃n.n < k ∧ P n). |
---|
| 100 | #P #HP_dec #k elim k -k |
---|
| 101 | [ %2 @nmk #Habs elim Habs #n #Hn @(absurd (n < 0) (proj1 … Hn)) @not_le_Sn_O |
---|
| 102 | | #k #Hind cases Hind |
---|
| 103 | [ #Hk %1 elim Hk #n #Hn @(ex_intro … n) @conj [ @le_S @(proj1 … Hn) | @(proj2 … Hn) ] |
---|
| 104 | | #Hk cases (HP_dec k) |
---|
| 105 | [ #HPk %1 @(ex_intro … k) @conj [ @le_n | @HPk ] |
---|
| 106 | | #HPk %2 @nmk #Habs elim Habs #n #Hn cases (le_to_or_lt_eq … (proj1 … Hn)) |
---|
| 107 | [ #H @(absurd (∃n.n < k ∧ P n)) [ @(ex_intro … n) @conj |
---|
| 108 | [ @(le_S_S_to_le … H) | @(proj2 … Hn) ] | @Hk ] |
---|
| 109 | | #H @(absurd (P k)) [ <(injective_S … H) @(proj2 … Hn) | @HPk ] |
---|
| 110 | ] |
---|
| 111 | ] |
---|
| 112 | ] |
---|
| 113 | ] |
---|
| 114 | qed. |
---|
| 115 | |
---|
[1930] | 116 | (* Replace decision functions by result. *) |
---|
| 117 | |
---|
| 118 | lemma dec_true: ∀P:Prop.∀f:P + ¬P.∀p:P.∀Q:(P + ¬P) → Type[0]. (∀p'.Q (inl ?? p')) → Q f. |
---|
| 119 | #P #f #p #Q #H cases f; |
---|
| 120 | [ @H |
---|
| 121 | | #np cut False [ @(absurd ? p np) | * ] |
---|
| 122 | ] qed. |
---|
| 123 | |
---|
| 124 | lemma dec_false: ∀P:Prop.∀f:P + ¬P.∀p:¬P.∀Q:(P + ¬P) → Type[0]. (∀p'.Q (inr ?? p')) → Q f. |
---|
| 125 | #P #f #p #Q #H cases f; |
---|
| 126 | [ #np cut False [ @(absurd ? np p) | * ] |
---|
| 127 | | @H |
---|
| 128 | ] qed. |
---|
| 129 | |
---|
| 130 | |
---|
[1593] | 131 | lemma not_exists_forall: |
---|
| 132 | ∀k:ℕ.∀P:ℕ → Prop.¬(∃x.x < k ∧ P x) → ∀x.x < k → ¬P x. |
---|
| 133 | #k #P #Hex #x #Hx @nmk #Habs @(absurd ? ? Hex) @(ex_intro … x) |
---|
| 134 | @conj [ @Hx | @Habs ] |
---|
| 135 | qed. |
---|
| 136 | |
---|
| 137 | lemma not_forall_exists: |
---|
| 138 | ∀k:ℕ.∀P:ℕ → Prop.(∀n.(P n) + (¬P n)) → ¬(∀x.x < k → P x) → ∃x.x < k ∧ ¬P x. |
---|
| 139 | #k #P #Hdec elim k |
---|
| 140 | [ #Hfa @⊥ @(absurd ?? Hfa) #z #Hz @⊥ @(absurd ? Hz) @not_le_Sn_O |
---|
| 141 | | -k #k #Hind #Hfa cases (Hdec k) |
---|
| 142 | [ #HP elim (Hind ?) |
---|
| 143 | [ -Hind; #x #Hx @(ex_intro ?? x) @conj [ @le_S @(proj1 ?? Hx) | @(proj2 ?? Hx) ] |
---|
| 144 | | @nmk #H @(absurd ?? Hfa) #x #Hx cases (le_to_or_lt_eq ?? Hx) |
---|
| 145 | [ #H2 @H @(le_S_S_to_le … H2) |
---|
| 146 | | #H2 >(injective_S … H2) @HP |
---|
| 147 | ] |
---|
| 148 | ] |
---|
| 149 | | #HP @(ex_intro … k) @conj [ @le_n | @HP ] |
---|
| 150 | ] |
---|
| 151 | ] |
---|
| 152 | qed. |
---|
[1882] | 153 | |
---|
| 154 | lemma associative_orb : associative ? orb. |
---|
| 155 | *** // qed. |
---|
| 156 | |
---|
| 157 | lemma commutative_orb : commutative ? orb. |
---|
| 158 | ** // qed. |
---|
| 159 | |
---|
| 160 | lemma associative_andb : associative ? andb. |
---|
| 161 | *** // qed. |
---|
| 162 | |
---|
| 163 | lemma commutative_andb : commutative ? andb. |
---|
| 164 | ** // qed. |
---|
| 165 | |
---|
| 166 | |
---|
| 167 | lemma notb_false : ∀b.(¬b) = false → b = true. |
---|
| 168 | * [#_ % | normalize #EQ destruct] |
---|
| 169 | qed. |
---|
| 170 | |
---|
| 171 | lemma notb_true : ∀b.(¬b) = true → b = false. |
---|
| 172 | * [normalize #EQ destruct | #_ %] |
---|
| 173 | qed. |
---|
| 174 | |
---|
| 175 | |
---|
| 176 | |
---|
| 177 | notation > "Σ 〈 ident x : tyx, ident y : tyy 〉 . P" with precedence 20 for |
---|
| 178 | @{'sigma (λ${fresh p}. |
---|
| 179 | match ${fresh p} with [mk_Prod (${ident x} : $tyx) (${ident y} : $tyy) ⇒ $P])}. |
---|
| 180 | notation > "Σ 〈 ident x, ident y 〉 . P" with precedence 20 for |
---|
| 181 | @{'sigma (λ${fresh p}. |
---|
| 182 | match ${fresh p} with [mk_Prod ${ident x} ${ident y} ⇒ $P])}. |
---|
| 183 | notation > "Σ 〈 ident x : tyx, ident y : tyy, ident z : tyz 〉 . P" with precedence 20 for |
---|
| 184 | @{'sigma (λ${fresh p1}. |
---|
| 185 | match ${fresh p1} with [mk_Prod ${fresh p2} (${ident z} : $tyz) ⇒ |
---|
| 186 | match ${fresh p2} with [mk_Prod (${ident x} : $tyx) (${ident y} : $tyy) ⇒ $P]])}. |
---|
| 187 | notation > "Σ 〈 ident x , ident y , ident z 〉 . P" with precedence 20 for |
---|
| 188 | @{'sigma (λ${fresh p1}. |
---|
| 189 | match ${fresh p1} with [mk_Prod ${fresh p2} ${ident z} ⇒ |
---|
| 190 | match ${fresh p2} with [mk_Prod ${ident x} ${ident y} ⇒ $P]])}. |
---|
| 191 | |
---|