# HG changeset patch # User huffman # Date 1214868340 -7200 # Node ID f65a889f97f909e81c6a3a88b364eb4a54df393b # Parent 22a515a55bf5f36addb3cecf39ec21c72455f86e theory of algebraic deflations diff -r 22a515a55bf5 -r f65a889f97f9 src/HOLCF/Algebraic.thy --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/HOLCF/Algebraic.thy Tue Jul 01 01:25:40 2008 +0200 @@ -0,0 +1,536 @@ +(* Title: HOLCF/Algebraic.thy + ID: $Id$ + Author: Brian Huffman +*) + +header {* Algebraic deflations *} + +theory Algebraic +imports Completion Fix Eventual +begin + +declare range_composition [simp del] + +subsection {* Constructing finite deflations by iteration *} + +lemma finite_deflation_imp_deflation: + "finite_deflation d \ deflation d" +unfolding finite_deflation_def by simp + +lemma le_Suc_induct: + assumes le: "i \ j" + assumes step: "\i. P i (Suc i)" + assumes refl: "\i. P i i" + assumes trans: "\i j k. \P i j; P j k\ \ P i k" + shows "P i j" +proof (cases "i = j") + assume "i = j" + thus "P i j" by (simp add: refl) +next + assume "i \ j" + with le have "i < j" by simp + thus "P i j" using step trans by (rule less_Suc_induct) +qed + +text {* A pre-deflation is like a deflation, but not idempotent. *} + +locale pre_deflation = + fixes f :: "'a \ 'a::cpo" + assumes less: "\x. f\x \ x" + assumes finite_range: "finite (range (\x. f\x))" +begin + +lemma iterate_less: "iterate i\f\x \ x" +by (induct i, simp_all add: trans_less [OF less]) + +lemma iterate_fixed: "f\x = x \ iterate i\f\x = x" +by (induct i, simp_all) + +lemma antichain_iterate_app: "i \ j \ iterate j\f\x \ iterate i\f\x" +apply (erule le_Suc_induct) +apply (simp add: less) +apply (rule refl_less) +apply (erule (1) trans_less) +done + +lemma finite_range_iterate_app: "finite (range (\i. iterate i\f\x))" +proof (rule finite_subset) + show "range (\i. iterate i\f\x) \ insert x (range (\x. f\x))" + by (clarify, case_tac i, simp_all) + show "finite (insert x (range (\x. f\x)))" + by (simp add: finite_range) +qed + +lemma eventually_constant_iterate_app: + "eventually_constant (\i. iterate i\f\x)" +unfolding eventually_constant_def MOST_nat_le +proof - + let ?Y = "\i. iterate i\f\x" + have "\j. \k. ?Y j \ ?Y k" + apply (rule finite_range_has_max) + apply (erule antichain_iterate_app) + apply (rule finite_range_iterate_app) + done + then obtain j where j: "\k. ?Y j \ ?Y k" by fast + show "\z m. \n\m. ?Y n = z" + proof (intro exI allI impI) + fix k + assume "j \ k" + hence "?Y k \ ?Y j" by (rule antichain_iterate_app) + also have "?Y j \ ?Y k" by (rule j) + finally show "?Y k = ?Y j" . + qed +qed + +lemma eventually_constant_iterate: + "eventually_constant (\n. iterate n\f)" +proof - + have "\y\range (\x. f\x). eventually_constant (\i. iterate i\f\y)" + by (simp add: eventually_constant_iterate_app) + hence "\y\range (\x. f\x). MOST i. MOST j. iterate j\f\y = iterate i\f\y" + unfolding eventually_constant_MOST_MOST . + hence "MOST i. MOST j. \y\range (\x. f\x). iterate j\f\y = iterate i\f\y" + by (simp only: MOST_finite_Ball_distrib [OF finite_range]) + hence "MOST i. MOST j. \x. iterate j\f\(f\x) = iterate i\f\(f\x)" + by simp + hence "MOST i. MOST j. \x. iterate (Suc j)\f\x = iterate (Suc i)\f\x" + by (simp only: iterate_Suc2) + hence "MOST i. MOST j. iterate (Suc j)\f = iterate (Suc i)\f" + by (simp only: expand_cfun_eq) + hence "eventually_constant (\i. iterate (Suc i)\f)" + unfolding eventually_constant_MOST_MOST . + thus "eventually_constant (\i. iterate i\f)" + by (rule eventually_constant_SucD) +qed + +abbreviation + d :: "'a \ 'a" +where + "d \ eventual (\n. iterate n\f)" + +lemma MOST_d: "MOST n. P (iterate n\f) \ P d" +using eventually_constant_iterate by (rule MOST_eventual) + +lemma f_d: "f\(d\x) = d\x" +apply (rule MOST_d) +apply (subst iterate_Suc [symmetric]) +apply (rule eventually_constant_MOST_Suc_eq) +apply (rule eventually_constant_iterate_app) +done + +lemma d_fixed_iff: "d\x = x \ f\x = x" +proof + assume "d\x = x" + with f_d [where x=x] + show "f\x = x" by simp +next + assume f: "f\x = x" + have "\n. iterate n\f\x = x" + by (rule allI, rule nat.induct, simp, simp add: f) + hence "MOST n. iterate n\f\x = x" + by (rule ALL_MOST) + thus "d\x = x" + by (rule MOST_d) +qed + +lemma finite_deflation_d: "finite_deflation d" +proof + fix x :: 'a + have "d \ range (\n. iterate n\f)" + using eventually_constant_iterate + by (rule eventual_mem_range) + then obtain n where n: "d = iterate n\f" .. + have "iterate n\f\(d\x) = d\x" + using f_d by (rule iterate_fixed) + thus "d\(d\x) = d\x" + by (simp add: n) +next + fix x :: 'a + show "d\x \ x" + by (rule MOST_d, simp add: iterate_less) +next + from finite_range + have "finite {x. f\x = x}" + by (rule finite_range_imp_finite_fixes) + thus "finite {x. d\x = x}" + by (simp add: d_fixed_iff) +qed + +end + +lemma pre_deflation_d_f: + includes finite_deflation d + assumes f: "\x. f\x \ x" + shows "pre_deflation (d oo f)" +proof + fix x + show "\x. (d oo f)\x \ x" + by (simp, rule trans_less [OF d.less f]) + show "finite (range (\x. (d oo f)\x))" + by (rule finite_subset [OF _ d.finite_range], auto) +qed + +lemma eventual_iterate_oo_fixed_iff: + includes finite_deflation d + assumes f: "\x. f\x \ x" + shows "eventual (\n. iterate n\(d oo f))\x = x \ d\x = x \ f\x = x" +proof - + let ?e = "d oo f" + interpret e: pre_deflation ["d oo f"] + using `finite_deflation d` f + by (rule pre_deflation_d_f) + let ?g = "eventual (\n. iterate n\?e)" + show ?thesis + apply (subst e.d_fixed_iff) + apply simp + apply safe + apply (erule subst) + apply (rule d.idem) + apply (rule antisym_less) + apply (rule f) + apply (erule subst, rule d.less) + apply simp + done +qed + +subsection {* Type constructor for finite deflations *} + +defaultsort profinite + +typedef (open) 'a fin_defl = "{d::'a \ 'a. finite_deflation d}" +by (fast intro: finite_deflation_approx) + +instantiation fin_defl :: (profinite) sq_ord +begin + +definition + sq_le_fin_defl_def: + "op \ \ \x y. Rep_fin_defl x \ Rep_fin_defl y" + +instance .. +end + +instance fin_defl :: (profinite) po +by (rule typedef_po [OF type_definition_fin_defl sq_le_fin_defl_def]) + +lemma finite_deflation_Rep_fin_defl: "finite_deflation (Rep_fin_defl d)" +using Rep_fin_defl by simp + +interpretation Rep_fin_defl: finite_deflation ["Rep_fin_defl d"] +by (rule finite_deflation_Rep_fin_defl) + +lemma fin_defl_lessI: + "(\x. Rep_fin_defl a\x = x \ Rep_fin_defl b\x = x) \ a \ b" +unfolding sq_le_fin_defl_def +by (rule Rep_fin_defl.lessI) + +lemma fin_defl_lessD: + "\a \ b; Rep_fin_defl a\x = x\ \ Rep_fin_defl b\x = x" +unfolding sq_le_fin_defl_def +by (rule Rep_fin_defl.lessD) + +lemma fin_defl_eqI: + "(\x. Rep_fin_defl a\x = x \ Rep_fin_defl b\x = x) \ a = b" +apply (rule antisym_less) +apply (rule fin_defl_lessI, simp) +apply (rule fin_defl_lessI, simp) +done + +lemma Abs_fin_defl_mono: + "\finite_deflation a; finite_deflation b; a \ b\ + \ Abs_fin_defl a \ Abs_fin_defl b" +unfolding sq_le_fin_defl_def +by (simp add: Abs_fin_defl_inverse) + + +subsection {* Take function for finite deflations *} + +definition + fd_take :: "nat \ 'a fin_defl \ 'a fin_defl" +where + "fd_take i d = Abs_fin_defl (eventual (\n. iterate n\(approx i oo Rep_fin_defl d)))" + +lemma Rep_fin_defl_fd_take: + "Rep_fin_defl (fd_take i d) = + eventual (\n. iterate n\(approx i oo Rep_fin_defl d))" +unfolding fd_take_def +apply (rule Abs_fin_defl_inverse [unfolded mem_Collect_eq]) +apply (rule pre_deflation.finite_deflation_d) +apply (rule pre_deflation_d_f) +apply (rule finite_deflation_approx) +apply (rule Rep_fin_defl.less) +done + +lemma fd_take_fixed_iff: + "Rep_fin_defl (fd_take i d)\x = x \ + approx i\x = x \ Rep_fin_defl d\x = x" +unfolding Rep_fin_defl_fd_take +by (rule eventual_iterate_oo_fixed_iff + [OF finite_deflation_approx Rep_fin_defl.less]) + +lemma fd_take_less: "fd_take n d \ d" +apply (rule fin_defl_lessI) +apply (simp add: fd_take_fixed_iff) +done + +lemma fd_take_idem: "fd_take n (fd_take n d) = fd_take n d" +apply (rule fin_defl_eqI) +apply (simp add: fd_take_fixed_iff) +done + +lemma fd_take_mono: "a \ b \ fd_take n a \ fd_take n b" +apply (rule fin_defl_lessI) +apply (simp add: fd_take_fixed_iff) +apply (simp add: fin_defl_lessD) +done + +lemma approx_fixed_le_lemma: "\i \ j; approx i\x = x\ \ approx j\x = x" +by (erule subst, simp add: min_def) + +lemma fd_take_chain: "m \ n \ fd_take m a \ fd_take n a" +apply (rule fin_defl_lessI) +apply (simp add: fd_take_fixed_iff) +apply (simp add: approx_fixed_le_lemma) +done + +lemma finite_range_fd_take: "finite (range (fd_take n))" +apply (rule finite_imageD [where f="\a. {x. Rep_fin_defl a\x = x}"]) +apply (rule finite_subset [where B="Pow {x. approx n\x = x}"]) +apply (clarify, simp add: fd_take_fixed_iff) +apply (simp add: finite_fixes_approx) +apply (rule inj_onI, clarify) +apply (simp add: expand_set_eq fin_defl_eqI) +done + +lemma fd_take_covers: "\n. fd_take n a = a" +apply (rule_tac x= + "Max ((\x. LEAST n. approx n\x = x) ` {x. Rep_fin_defl a\x = x})" in exI) +apply (rule antisym_less) +apply (rule fd_take_less) +apply (rule fin_defl_lessI) +apply (simp add: fd_take_fixed_iff) +apply (rule approx_fixed_le_lemma) +apply (rule Max_ge) +apply (rule finite_imageI) +apply (rule Rep_fin_defl.finite_fixes) +apply (rule imageI) +apply (erule CollectI) +apply (rule LeastI_ex) +apply (rule profinite_compact_eq_approx) +apply (erule subst) +apply (rule Rep_fin_defl.compact) +done + +interpretation fin_defl: basis_take [sq_le fd_take] +apply default +apply (rule fd_take_less) +apply (rule fd_take_idem) +apply (erule fd_take_mono) +apply (rule fd_take_chain, simp) +apply (rule finite_range_fd_take) +apply (rule fd_take_covers) +done + +subsection {* Defining algebraic deflations by ideal completion *} + +typedef (open) 'a alg_defl = + "{S::'a fin_defl set. sq_le.ideal S}" +by (fast intro: sq_le.ideal_principal) + +instantiation alg_defl :: (profinite) sq_ord +begin + +definition + "x \ y \ Rep_alg_defl x \ Rep_alg_defl y" + +instance .. +end + +instance alg_defl :: (profinite) po +by (rule sq_le.typedef_ideal_po + [OF type_definition_alg_defl sq_le_alg_defl_def]) + +instance alg_defl :: (profinite) cpo +by (rule sq_le.typedef_ideal_cpo + [OF type_definition_alg_defl sq_le_alg_defl_def]) + +lemma Rep_alg_defl_lub: + "chain Y \ Rep_alg_defl (\i. Y i) = (\i. Rep_alg_defl (Y i))" +by (rule sq_le.typedef_ideal_rep_contlub + [OF type_definition_alg_defl sq_le_alg_defl_def]) + +lemma ideal_Rep_alg_defl: "sq_le.ideal (Rep_alg_defl xs)" +by (rule Rep_alg_defl [unfolded mem_Collect_eq]) + +definition + alg_defl_principal :: "'a fin_defl \ 'a alg_defl" where + "alg_defl_principal t = Abs_alg_defl {u. u \ t}" + +lemma Rep_alg_defl_principal: + "Rep_alg_defl (alg_defl_principal t) = {u. u \ t}" +unfolding alg_defl_principal_def +by (simp add: Abs_alg_defl_inverse sq_le.ideal_principal) + +interpretation alg_defl: + ideal_completion [sq_le fd_take alg_defl_principal Rep_alg_defl] +apply default +apply (rule ideal_Rep_alg_defl) +apply (erule Rep_alg_defl_lub) +apply (rule Rep_alg_defl_principal) +apply (simp only: sq_le_alg_defl_def) +done + +text {* Algebraic deflations are pointed *} + +lemma finite_deflation_UU: "finite_deflation \" +by default simp_all + +lemma alg_defl_minimal: + "alg_defl_principal (Abs_fin_defl \) \ x" +apply (induct x rule: alg_defl.principal_induct, simp) +apply (rule alg_defl.principal_mono) +apply (induct_tac a) +apply (rule Abs_fin_defl_mono) +apply (rule finite_deflation_UU) +apply simp +apply (rule minimal) +done + +instance alg_defl :: (bifinite) pcpo +by intro_classes (fast intro: alg_defl_minimal) + +lemma inst_alg_defl_pcpo: "\ = alg_defl_principal (Abs_fin_defl \)" +by (rule alg_defl_minimal [THEN UU_I, symmetric]) + +text {* Algebraic deflations are profinite *} + +instantiation alg_defl :: (profinite) profinite +begin + +definition + approx_alg_defl_def: "approx = alg_defl.completion_approx" + +instance +apply (intro_classes, unfold approx_alg_defl_def) +apply (rule alg_defl.chain_completion_approx) +apply (rule alg_defl.lub_completion_approx) +apply (rule alg_defl.completion_approx_idem) +apply (rule alg_defl.finite_fixes_completion_approx) +done + +end + +instance alg_defl :: (bifinite) bifinite .. + +lemma approx_alg_defl_principal [simp]: + "approx n\(alg_defl_principal t) = alg_defl_principal (fd_take n t)" +unfolding approx_alg_defl_def +by (rule alg_defl.completion_approx_principal) + +lemma approx_eq_alg_defl_principal: + "\t\Rep_alg_defl xs. approx n\xs = alg_defl_principal (fd_take n t)" +unfolding approx_alg_defl_def +by (rule alg_defl.completion_approx_eq_principal) + + +subsection {* Applying algebraic deflations *} + +definition + cast :: "'a alg_defl \ 'a \ 'a" +where + "cast = alg_defl.basis_fun Rep_fin_defl" + +lemma cast_alg_defl_principal: + "cast\(alg_defl_principal a) = Rep_fin_defl a" +unfolding cast_def +apply (rule alg_defl.basis_fun_principal) +apply (simp only: sq_le_fin_defl_def) +done + +lemma deflation_cast: "deflation (cast\d)" +apply (induct d rule: alg_defl.principal_induct) +apply (rule adm_subst [OF _ adm_deflation], simp) +apply (simp add: cast_alg_defl_principal) +apply (rule finite_deflation_imp_deflation) +apply (rule finite_deflation_Rep_fin_defl) +done + +lemma finite_deflation_cast: + "compact d \ finite_deflation (cast\d)" +apply (drule alg_defl.compact_imp_principal, clarify) +apply (simp add: cast_alg_defl_principal) +apply (rule finite_deflation_Rep_fin_defl) +done + +interpretation cast: deflation ["cast\d"] +by (rule deflation_cast) + +lemma "cast\(\i. alg_defl_principal (Abs_fin_defl (approx i)))\x = x" +apply (subst contlub_cfun_arg) +apply (rule chainI) +apply (rule alg_defl.principal_mono) +apply (rule Abs_fin_defl_mono) +apply (rule finite_deflation_approx) +apply (rule finite_deflation_approx) +apply (rule chainE) +apply (rule chain_approx) +apply (simp add: cast_alg_defl_principal Abs_fin_defl_inverse finite_deflation_approx) +done + +text {* This lemma says that if we have an ep-pair from +a bifinite domain into a universal domain, then e oo p +is an algebraic deflation. *} + +lemma + includes ep_pair e p + constrains e :: "'a::profinite \ 'b::profinite" + shows "\d. cast\d = e oo p" +proof + let ?a = "\i. e oo approx i oo p" + have a: "\i. finite_deflation (?a i)" + apply (rule finite_deflation_e_d_p) + apply (rule finite_deflation_approx) + done + let ?d = "\i. alg_defl_principal (Abs_fin_defl (?a i))" + show "cast\?d = e oo p" + apply (subst contlub_cfun_arg) + apply (rule chainI) + apply (rule alg_defl.principal_mono) + apply (rule Abs_fin_defl_mono [OF a a]) + apply (rule chainE, simp) + apply (subst cast_alg_defl_principal) + apply (simp add: Abs_fin_defl_inverse a) + apply (simp add: expand_cfun_eq lub_distribs) + done +qed + +text {* This lemma says that if we have an ep-pair +from a cpo into a bifinite domain, and e oo p is +an algebraic deflation, then the cpo is bifinite. *} + +lemma + includes ep_pair e p + constrains e :: "'a::cpo \ 'b::profinite" + assumes d: "\x. cast\d\x = e\(p\x)" + obtains a :: "nat \ 'a \ 'a" where + "\i. finite_deflation (a i)" + "(\i. a i) = ID" +proof + let ?a = "\i. p oo cast\(approx i\d) oo e" + show "\i. finite_deflation (?a i)" + apply (rule finite_deflation_p_d_e) + apply (rule finite_deflation_cast) + apply (rule compact_approx) + apply (rule sq_ord_less_eq_trans [OF _ d]) + apply (rule monofun_cfun_fun) + apply (rule monofun_cfun_arg) + apply (rule approx_less) + done + show "(\i. ?a i) = ID" + apply (rule ext_cfun, simp) + apply (simp add: lub_distribs) + apply (simp add: d) + done +qed + +end