X-Git-Url: http://matita.cs.unibo.it/gitweb/?p=helm.git;a=blobdiff_plain;f=matita%2Flibrary%2Fnat%2Fbinomial.ma;fp=matita%2Flibrary%2Fnat%2Fbinomial.ma;h=83ef0acbb99d54f43ec260f16dc60447966be230;hp=0000000000000000000000000000000000000000;hb=f61af501fb4608cc4fb062a0864c774e677f0d76;hpb=58ae1809c352e71e7b5530dc41e2bfc834e1aef1 diff --git a/matita/library/nat/binomial.ma b/matita/library/nat/binomial.ma new file mode 100644 index 000000000..83ef0acbb --- /dev/null +++ b/matita/library/nat/binomial.ma @@ -0,0 +1,260 @@ +(**************************************************************************) +(* __ *) +(* ||M|| *) +(* ||A|| A project by Andrea Asperti *) +(* ||T|| *) +(* ||I|| Developers: *) +(* ||T|| A.Asperti, C.Sacerdoti Coen, *) +(* ||A|| E.Tassi, S.Zacchiroli *) +(* \ / *) +(* \ / This file is distributed under the terms of the *) +(* v GNU Lesser General Public License Version 2.1 *) +(* *) +(**************************************************************************) + +include "nat/iteration2.ma". +include "nat/factorial2.ma". + +definition bc \def \lambda n,k. n!/(k!*(n-k)!). + +theorem bc_n_n: \forall n. bc n n = S O. +intro.unfold bc. +rewrite < minus_n_n. +simplify in ⊢ (? ? (? ? (? ? %)) ?). +rewrite < times_n_SO. +apply div_n_n. +apply lt_O_fact. +qed. + +theorem bc_n_O: \forall n. bc n O = S O. +intro.unfold bc. +rewrite < minus_n_O. +simplify in ⊢ (? ? (? ? %) ?). +rewrite < plus_n_O. +apply div_n_n. +apply lt_O_fact. +qed. + +theorem fact_minus: \forall n,k. k < n \to +(n-k)*(n - S k)! = (n - k)!. +intros 2.cases n + [intro.apply False_ind. + apply (lt_to_not_le ? ? H). + apply le_O_n + |intros. + rewrite > minus_Sn_m. + reflexivity. + apply le_S_S_to_le. + assumption + ] +qed. + +theorem bc2 : \forall n. +\forall k. k \leq n \to divides (k!*(n-k)!) n!. +intro;elim n + [rewrite < (le_n_O_to_eq ? H);apply reflexive_divides + |generalize in match H1;cases k + [intro;simplify in ⊢ (? (? ? (? %)) ?);simplify in ⊢ (? (? % ?) ?); + rewrite > sym_times;rewrite < times_n_SO;apply reflexive_divides + |intro;elim (decidable_eq_nat n2 n1) + [rewrite > H3;rewrite < minus_n_n; + rewrite > times_n_SO in ⊢ (? ? %);apply reflexive_divides + |lapply (H n2) + [lapply (H (n1 - (S n2))) + [change in ⊢ (? ? %) with ((S n1)*n1!); + rewrite > (plus_minus_m_m n1 n2) in ⊢ (? ? (? (? %) ?)) + [rewrite > sym_plus; + change in ⊢ (? ? (? % ?)) with ((S n2) + (n1 - n2)); + rewrite > sym_times in \vdash (? ? %); + rewrite > distr_times_plus in ⊢ (? ? %); + simplify in ⊢ (? (? ? (? %)) ?); + apply divides_plus + [rewrite > sym_times; + change in ⊢ (? (? ? %) ?) with ((S n2)*n2!); + rewrite > sym_times in ⊢ (? (? ? %) ?); + rewrite < assoc_times; + apply divides_times + [rewrite > sym_times;assumption + |apply reflexive_divides] + |rewrite < fact_minus in ⊢ (? (? ? %) ?) + [rewrite > sym_times in ⊢ (? (? ? %) ?); + rewrite < assoc_times; + apply divides_times + [rewrite < eq_plus_minus_minus_minus in Hletin1; + [rewrite > sym_times;rewrite < minus_n_n in Hletin1; + rewrite < plus_n_O in Hletin1;assumption + |lapply (le_S_S_to_le ? ? H2); + elim (le_to_or_lt_eq ? ? Hletin2); + [assumption + |elim (H3 H4)] + |constructor 1] + |apply reflexive_divides] + |lapply (le_S_S_to_le ? ? H2); + elim (le_to_or_lt_eq ? ? Hletin2); + [assumption + |elim (H3 H4)]]] + |apply le_S_S_to_le;assumption] + |apply le_minus_m;apply le_S_S_to_le;assumption] + |apply le_S_S_to_le;assumption]]]] +qed. + +theorem bc1: \forall n.\forall k. k < n \to bc (S n) (S k) = (bc n k) + (bc n (S k)). +intros.unfold bc. +rewrite > (lt_to_lt_to_eq_div_div_times_times ? ? (S k)) in ⊢ (? ? ? (? % ?)) + [rewrite > sym_times in ⊢ (? ? ? (? (? ? %) ?)). + rewrite < assoc_times in ⊢ (? ? ? (? (? ? %) ?)). + rewrite > (lt_to_lt_to_eq_div_div_times_times ? ? (n - k)) in ⊢ (? ? ? (? ? %)) + [rewrite > assoc_times in ⊢ (? ? ? (? ? (? ? %))). + rewrite > sym_times in ⊢ (? ? ? (? ? (? ? (? ? %)))). + rewrite > fact_minus + [rewrite < eq_div_plus + [rewrite < distr_times_plus. + simplify in ⊢ (? ? ? (? (? ? %) ?)). + rewrite > sym_plus in ⊢ (? ? ? (? (? ? (? %)) ?)). + rewrite < plus_minus_m_m + [rewrite > sym_times in ⊢ (? ? ? (? % ?)). + reflexivity + |apply lt_to_le. + assumption + ] + |rewrite > (times_n_O O). + apply lt_times;apply lt_O_fact + |change in ⊢ (? (? % ?) ?) with ((S k)*k!); + rewrite < sym_times in ⊢ (? ? %); + rewrite > assoc_times;apply divides_times + [apply reflexive_divides + |apply bc2;apply le_S_S_to_le;constructor 2;assumption] + |rewrite < fact_minus + [rewrite > sym_times in ⊢ (? (? ? %) ?);rewrite < assoc_times; + apply divides_times + [apply bc2;assumption + |apply reflexive_divides] + |assumption]] + |assumption] + |apply lt_to_lt_O_minus;assumption + |rewrite > (times_n_O O). + apply lt_times;apply lt_O_fact] +|apply lt_O_S +|rewrite > (times_n_O O). + apply lt_times;apply lt_O_fact] +qed. + +theorem lt_O_bc: \forall n,m. m \le n \to O < bc n m. +intro.elim n + [apply (le_n_O_elim ? H). + simplify.apply le_n + |elim (le_to_or_lt_eq ? ? H1) + [generalize in match H2.cases m;intro + [rewrite > bc_n_O.apply le_n + |rewrite > bc1 + [apply (trans_le ? (bc n1 n2)) + [apply H.apply le_S_S_to_le.apply lt_to_le.assumption + |apply le_plus_n_r + ] + |apply le_S_S_to_le.assumption + ] + ] + |rewrite > H2. + rewrite > bc_n_n. + apply le_n + ] + ] +qed. + +theorem exp_plus_sigma_p:\forall a,b,n. +exp (a+b) n = sigma_p (S n) (\lambda k.true) + (\lambda k.(bc n k)*(exp a (n-k))*(exp b k)). +intros.elim n + [simplify.reflexivity + |simplify in ⊢ (? ? % ?). + rewrite > true_to_sigma_p_Sn + [rewrite > H;rewrite > sym_times in ⊢ (? ? % ?); + rewrite > distr_times_plus in ⊢ (? ? % ?); + rewrite < minus_n_n in ⊢ (? ? ? (? (? (? ? (? ? %)) ?) ?)); + rewrite > sym_times in ⊢ (? ? (? % ?) ?); + rewrite > sym_times in ⊢ (? ? (? ? %) ?); + rewrite > distributive_times_plus_sigma_p in ⊢ (? ? (? % ?) ?); + rewrite > distributive_times_plus_sigma_p in ⊢ (? ? (? ? %) ?); + rewrite > true_to_sigma_p_Sn in ⊢ (? ? (? ? %) ?) + [rewrite < assoc_plus;rewrite < sym_plus in ⊢ (? ? (? % ?) ?); + rewrite > assoc_plus; + apply eq_f2 + [rewrite > sym_times;rewrite > assoc_times;autobatch paramodulation + |rewrite > (sigma_p_gi ? ? O); + [rewrite < (eq_sigma_p_gh ? S pred n1 (S n1) (λx:nat.true)) in ⊢ (? ? (? (? ? %) ?) ?) + [rewrite > (sigma_p_gi ? ? O) in ⊢ (? ? ? %); + [rewrite > assoc_plus;apply eq_f2 + [autobatch paramodulation; + |rewrite < sigma_p_plus_1; + rewrite < (eq_sigma_p_gh ? S pred n1 (S n1) (λx:nat.true)) in \vdash (? ? ? %); + [apply eq_sigma_p + [intros;reflexivity + |intros;rewrite > sym_times;rewrite > assoc_times; + rewrite > sym_times in ⊢ (? ? (? (? ? %) ?) ?); + rewrite > assoc_times;rewrite < assoc_times in ⊢ (? ? (? (? ? %) ?) ?); + rewrite > sym_times in ⊢ (? ? (? (? ? (? % ?)) ?) ?); + change in ⊢ (? ? (? (? ? (? % ?)) ?) ?) with (exp a (S (n1 - S x))); + rewrite < (minus_Sn_m ? ? H1);rewrite > minus_S_S; + rewrite > sym_times in \vdash (? ? (? ? %) ?); + rewrite > assoc_times; + rewrite > sym_times in ⊢ (? ? (? ? (? ? %)) ?); + change in \vdash (? ? (? ? (? ? %)) ?) with (exp b (S x)); + rewrite > assoc_times in \vdash (? ? (? ? %) ?); + rewrite > sym_times in \vdash (? ? (? % ?) ?); + rewrite > sym_times in \vdash (? ? (? ? %) ?); + rewrite > assoc_times in \vdash (? ? ? %); + rewrite > sym_times in \vdash (? ? ? %); + rewrite < distr_times_plus; + rewrite > sym_plus;rewrite < bc1; + [reflexivity|assumption]] + |intros;simplify;reflexivity + |intros;simplify;reflexivity + |intros;apply le_S_S;assumption + |intros;reflexivity + |intros 2;elim j + [simplify in H2;destruct H2 + |simplify;reflexivity] + |intro;elim j + [simplify in H2;destruct H2 + |simplify;apply le_S_S_to_le;assumption]]] + |apply le_S_S;apply le_O_n + |reflexivity] + |intros;simplify;reflexivity + |intros;simplify;reflexivity + |intros;apply le_S_S;assumption + |intros;reflexivity + |intros 2;elim j + [simplify in H2;destruct H2 + |simplify;reflexivity] + |intro;elim j + [simplify in H2;destruct H2 + |simplify;apply le_S_S_to_le;assumption]] + |apply le_S_S;apply le_O_n + |reflexivity]] + |reflexivity] + |reflexivity]] +qed. + +theorem exp_S_sigma_p:\forall a,n. +exp (S a) n = sigma_p (S n) (\lambda k.true) (\lambda k.(bc n k)*(exp a (n-k))). +intros. +rewrite > plus_n_SO. +rewrite > exp_plus_sigma_p. +apply eq_sigma_p;intros + [reflexivity + |rewrite < exp_SO_n. + rewrite < times_n_SO. + reflexivity + ] +qed. + +theorem exp_Sn_SSO: \forall n. exp (S n) 2 = S((exp n 2) + 2*n). +intros.simplify. +rewrite < times_n_SO. +rewrite < plus_n_O. +rewrite < sym_times.simplify. +rewrite < assoc_plus. +rewrite < sym_plus. +reflexivity. +qed. +