src/ZF/Perm.ML
changeset 5147 825877190618
parent 5143 b94cd208f073
child 5202 084ceb3844f5
equal deleted inserted replaced
5146:1ea751ae62b2 5147:825877190618
    56 by (etac CollectD1 1);
    56 by (etac CollectD1 1);
    57 qed "inj_is_fun";
    57 qed "inj_is_fun";
    58 
    58 
    59 (*Good for dealing with sets of pairs, but a bit ugly in use [used in AC]*)
    59 (*Good for dealing with sets of pairs, but a bit ugly in use [used in AC]*)
    60 Goalw [inj_def]
    60 Goalw [inj_def]
    61     "!!f A B. [| <a,b>:f;  <c,b>:f;  f: inj(A,B) |] ==> a=c";
    61     "[| <a,b>:f;  <c,b>:f;  f: inj(A,B) |] ==> a=c";
    62 by (REPEAT (eresolve_tac [asm_rl, Pair_mem_PiE, CollectE] 1));
    62 by (REPEAT (eresolve_tac [asm_rl, Pair_mem_PiE, CollectE] 1));
    63 by (Blast_tac 1);
    63 by (Blast_tac 1);
    64 qed "inj_equality";
    64 qed "inj_equality";
    65 
    65 
    66 Goalw [inj_def] "[| f:inj(A,B);  a:A;  b:A;  f`a=f`b |] ==> a=b";
    66 Goalw [inj_def] "[| f:inj(A,B);  a:A;  b:A;  f`a=f`b |] ==> a=b";
   166 
   166 
   167 (** Equations for converse(f) **)
   167 (** Equations for converse(f) **)
   168 
   168 
   169 (*The premises are equivalent to saying that f is injective...*) 
   169 (*The premises are equivalent to saying that f is injective...*) 
   170 Goal
   170 Goal
   171     "!!f. [| f: A->B;  converse(f): C->A;  a: A |] ==> converse(f)`(f`a) = a";
   171     "[| f: A->B;  converse(f): C->A;  a: A |] ==> converse(f)`(f`a) = a";
   172 by (blast_tac (claset() addIs [apply_Pair, apply_equality, converseI]) 1);
   172 by (blast_tac (claset() addIs [apply_Pair, apply_equality, converseI]) 1);
   173 qed "left_inverse_lemma";
   173 qed "left_inverse_lemma";
   174 
   174 
   175 Goal
   175 Goal
   176     "!!f. [| f: inj(A,B);  a: A |] ==> converse(f)`(f`a) = a";
   176     "[| f: inj(A,B);  a: A |] ==> converse(f)`(f`a) = a";
   177 by (blast_tac (claset() addIs [left_inverse_lemma, inj_converse_fun,
   177 by (blast_tac (claset() addIs [left_inverse_lemma, inj_converse_fun,
   178 			      inj_is_fun]) 1);
   178 			      inj_is_fun]) 1);
   179 qed "left_inverse";
   179 qed "left_inverse";
   180 
   180 
   181 val left_inverse_bij = bij_is_inj RS left_inverse;
   181 val left_inverse_bij = bij_is_inj RS left_inverse;
   305 
   305 
   306 
   306 
   307 (** Composition preserves functions, injections, and surjections **)
   307 (** Composition preserves functions, injections, and surjections **)
   308 
   308 
   309 Goalw [function_def]
   309 Goalw [function_def]
   310     "!!f g. [| function(g);  function(f) |] ==> function(f O g)";
   310     "[| function(g);  function(f) |] ==> function(f O g)";
   311 by (Blast_tac 1);
   311 by (Blast_tac 1);
   312 qed "comp_function";
   312 qed "comp_function";
   313 
   313 
   314 Goal "[| g: A->B;  f: B->C |] ==> (f O g) : A->C";
   314 Goal "[| g: A->B;  f: B->C |] ==> (f O g) : A->C";
   315 by (asm_full_simp_tac
   315 by (asm_full_simp_tac
   345 by (asm_simp_tac (simpset()  addsimps [left_inverse] 
   345 by (asm_simp_tac (simpset()  addsimps [left_inverse] 
   346                         setSolver type_auto_tac [inj_is_fun, apply_type]) 1);
   346                         setSolver type_auto_tac [inj_is_fun, apply_type]) 1);
   347 qed "comp_inj";
   347 qed "comp_inj";
   348 
   348 
   349 Goalw [surj_def]
   349 Goalw [surj_def]
   350     "!!f g. [| g: surj(A,B);  f: surj(B,C) |] ==> (f O g) : surj(A,C)";
   350     "[| g: surj(A,B);  f: surj(B,C) |] ==> (f O g) : surj(A,C)";
   351 by (blast_tac (claset() addSIs [comp_fun,comp_fun_apply]) 1);
   351 by (blast_tac (claset() addSIs [comp_fun,comp_fun_apply]) 1);
   352 qed "comp_surj";
   352 qed "comp_surj";
   353 
   353 
   354 Goalw [bij_def]
   354 Goalw [bij_def]
   355     "!!f g. [| g: bij(A,B);  f: bij(B,C) |] ==> (f O g) : bij(A,C)";
   355     "[| g: bij(A,B);  f: bij(B,C) |] ==> (f O g) : bij(A,C)";
   356 by (blast_tac (claset() addIs [comp_inj,comp_surj]) 1);
   356 by (blast_tac (claset() addIs [comp_inj,comp_surj]) 1);
   357 qed "comp_bij";
   357 qed "comp_bij";
   358 
   358 
   359 
   359 
   360 (** Dual properties of inj and surj -- useful for proofs from
   360 (** Dual properties of inj and surj -- useful for proofs from
   361     D Pastre.  Automatic theorem proving in set theory. 
   361     D Pastre.  Automatic theorem proving in set theory. 
   362     Artificial Intelligence, 10:1--27, 1978. **)
   362     Artificial Intelligence, 10:1--27, 1978. **)
   363 
   363 
   364 Goalw [inj_def]
   364 Goalw [inj_def]
   365     "!!f g. [| (f O g): inj(A,C);  g: A->B;  f: B->C |] ==> g: inj(A,B)";
   365     "[| (f O g): inj(A,C);  g: A->B;  f: B->C |] ==> g: inj(A,B)";
   366 by Safe_tac;
   366 by Safe_tac;
   367 by (REPEAT (eresolve_tac [asm_rl, bspec RS bspec RS mp] 1));
   367 by (REPEAT (eresolve_tac [asm_rl, bspec RS bspec RS mp] 1));
   368 by (asm_simp_tac (simpset() ) 1);
   368 by (asm_simp_tac (simpset() ) 1);
   369 qed "comp_mem_injD1";
   369 qed "comp_mem_injD1";
   370 
   370 
   371 Goalw [inj_def,surj_def]
   371 Goalw [inj_def,surj_def]
   372     "!!f g. [| (f O g): inj(A,C);  g: surj(A,B);  f: B->C |] ==> f: inj(B,C)";
   372     "[| (f O g): inj(A,C);  g: surj(A,B);  f: B->C |] ==> f: inj(B,C)";
   373 by Safe_tac;
   373 by Safe_tac;
   374 by (res_inst_tac [("x1", "x")] (bspec RS bexE) 1);
   374 by (res_inst_tac [("x1", "x")] (bspec RS bexE) 1);
   375 by (eres_inst_tac [("x1", "w")] (bspec RS bexE) 3);
   375 by (eres_inst_tac [("x1", "w")] (bspec RS bexE) 3);
   376 by (REPEAT (assume_tac 1));
   376 by (REPEAT (assume_tac 1));
   377 by Safe_tac;
   377 by Safe_tac;
   379 by (REPEAT (eresolve_tac [asm_rl, bspec RS bspec RS mp] 1));
   379 by (REPEAT (eresolve_tac [asm_rl, bspec RS bspec RS mp] 1));
   380 by (asm_simp_tac (simpset() ) 1);
   380 by (asm_simp_tac (simpset() ) 1);
   381 qed "comp_mem_injD2";
   381 qed "comp_mem_injD2";
   382 
   382 
   383 Goalw [surj_def]
   383 Goalw [surj_def]
   384     "!!f g. [| (f O g): surj(A,C);  g: A->B;  f: B->C |] ==> f: surj(B,C)";
   384     "[| (f O g): surj(A,C);  g: A->B;  f: B->C |] ==> f: surj(B,C)";
   385 by (blast_tac (claset() addSIs [comp_fun_apply RS sym, apply_funtype]) 1);
   385 by (blast_tac (claset() addSIs [comp_fun_apply RS sym, apply_funtype]) 1);
   386 qed "comp_mem_surjD1";
   386 qed "comp_mem_surjD1";
   387 
   387 
   388 Goal
   388 Goal
   389     "!!f g. [| (f O g)`a = c;  g: A->B;  f: B->C;  a:A |] ==> f`(g`a) = c";
   389     "[| (f O g)`a = c;  g: A->B;  f: B->C;  a:A |] ==> f`(g`a) = c";
   390 by (REPEAT (ares_tac [comp_fun_apply RS sym RS trans] 1));
   390 by (REPEAT (ares_tac [comp_fun_apply RS sym RS trans] 1));
   391 qed "comp_fun_applyD";
   391 qed "comp_fun_applyD";
   392 
   392 
   393 Goalw [inj_def,surj_def]
   393 Goalw [inj_def,surj_def]
   394     "!!f g. [| (f O g): surj(A,C);  g: A->B;  f: inj(B,C) |] ==> g: surj(A,B)";
   394     "[| (f O g): surj(A,C);  g: A->B;  f: inj(B,C) |] ==> g: surj(A,B)";
   395 by Safe_tac;
   395 by Safe_tac;
   396 by (eres_inst_tac [("x1", "f`y")] (bspec RS bexE) 1);
   396 by (eres_inst_tac [("x1", "f`y")] (bspec RS bexE) 1);
   397 by (REPEAT (ares_tac [apply_type] 1 ORELSE dtac comp_fun_applyD 1));
   397 by (REPEAT (ares_tac [apply_type] 1 ORELSE dtac comp_fun_applyD 1));
   398 by (blast_tac (claset() addSIs [apply_funtype]) 1);
   398 by (blast_tac (claset() addSIs [apply_funtype]) 1);
   399 qed "comp_mem_surjD2";
   399 qed "comp_mem_surjD2";
   422 qed "right_comp_inverse";
   422 qed "right_comp_inverse";
   423 
   423 
   424 (** Proving that a function is a bijection **)
   424 (** Proving that a function is a bijection **)
   425 
   425 
   426 Goalw [id_def]
   426 Goalw [id_def]
   427     "!!f A B. [| f: A->B;  g: B->A |] ==> \
   427     "[| f: A->B;  g: B->A |] ==> \
   428 \             f O g = id(B) <-> (ALL y:B. f`(g`y)=y)";
   428 \             f O g = id(B) <-> (ALL y:B. f`(g`y)=y)";
   429 by Safe_tac;
   429 by Safe_tac;
   430 by (dres_inst_tac [("t", "%h. h`y ")] subst_context 1);
   430 by (dres_inst_tac [("t", "%h. h`y ")] subst_context 1);
   431 by (Asm_full_simp_tac 1);
   431 by (Asm_full_simp_tac 1);
   432 by (rtac fun_extension 1);
   432 by (rtac fun_extension 1);
   433 by (REPEAT (ares_tac [comp_fun, lam_type] 1));
   433 by (REPEAT (ares_tac [comp_fun, lam_type] 1));
   434 by Auto_tac;
   434 by Auto_tac;
   435 qed "comp_eq_id_iff";
   435 qed "comp_eq_id_iff";
   436 
   436 
   437 Goalw [bij_def]
   437 Goalw [bij_def]
   438     "!!f A B. [| f: A->B;  g: B->A;  f O g = id(B);  g O f = id(A) \
   438     "[| f: A->B;  g: B->A;  f O g = id(B);  g O f = id(A) \
   439 \             |] ==> f : bij(A,B)";
   439 \             |] ==> f : bij(A,B)";
   440 by (asm_full_simp_tac (simpset() addsimps [comp_eq_id_iff]) 1);
   440 by (asm_full_simp_tac (simpset() addsimps [comp_eq_id_iff]) 1);
   441 by (REPEAT (ares_tac [conjI, f_imp_injective, f_imp_surjective] 1
   441 by (REPEAT (ares_tac [conjI, f_imp_injective, f_imp_surjective] 1
   442        ORELSE eresolve_tac [bspec, apply_type] 1));
   442        ORELSE eresolve_tac [bspec, apply_type] 1));
   443 qed "fg_imp_bijective";
   443 qed "fg_imp_bijective";
   453 
   453 
   454 (** Unions of functions -- cf similar theorems on func.ML **)
   454 (** Unions of functions -- cf similar theorems on func.ML **)
   455 
   455 
   456 (*Theorem by KG, proof by LCP*)
   456 (*Theorem by KG, proof by LCP*)
   457 Goal
   457 Goal
   458     "!!f g. [| f: inj(A,B);  g: inj(C,D);  B Int D = 0 |] ==> \
   458     "[| f: inj(A,B);  g: inj(C,D);  B Int D = 0 |] ==> \
   459 \           (lam a: A Un C. if(a:A, f`a, g`a)) : inj(A Un C, B Un D)";
   459 \           (lam a: A Un C. if(a:A, f`a, g`a)) : inj(A Un C, B Un D)";
   460 by (res_inst_tac [("d","%z. if(z:B, converse(f)`z, converse(g)`z)")]
   460 by (res_inst_tac [("d","%z. if(z:B, converse(f)`z, converse(g)`z)")]
   461         lam_injective 1);
   461         lam_injective 1);
   462 by (ALLGOALS 
   462 by (ALLGOALS 
   463     (asm_simp_tac (simpset() addsimps [inj_is_fun RS apply_type, left_inverse] 
   463     (asm_simp_tac (simpset() addsimps [inj_is_fun RS apply_type, left_inverse] 
   464                          setloop (split_tac [split_if] ORELSE' etac UnE))));
   464                          setloop (split_tac [split_if] ORELSE' etac UnE))));
   465 by (blast_tac (claset() addIs [inj_is_fun RS apply_type] addDs [equals0D]) 1);
   465 by (blast_tac (claset() addIs [inj_is_fun RS apply_type] addDs [equals0D]) 1);
   466 qed "inj_disjoint_Un";
   466 qed "inj_disjoint_Un";
   467 
   467 
   468 Goalw [surj_def]
   468 Goalw [surj_def]
   469     "!!f g. [| f: surj(A,B);  g: surj(C,D);  A Int C = 0 |] ==> \
   469     "[| f: surj(A,B);  g: surj(C,D);  A Int C = 0 |] ==> \
   470 \           (f Un g) : surj(A Un C, B Un D)";
   470 \           (f Un g) : surj(A Un C, B Un D)";
   471 by (blast_tac (claset() addIs [fun_disjoint_apply1, fun_disjoint_apply2,
   471 by (blast_tac (claset() addIs [fun_disjoint_apply1, fun_disjoint_apply2,
   472 			      fun_disjoint_Un, trans]) 1);
   472 			      fun_disjoint_Un, trans]) 1);
   473 qed "surj_disjoint_Un";
   473 qed "surj_disjoint_Un";
   474 
   474 
   475 (*A simple, high-level proof; the version for injections follows from it,
   475 (*A simple, high-level proof; the version for injections follows from it,
   476   using  f:inj(A,B) <-> f:bij(A,range(f))  *)
   476   using  f:inj(A,B) <-> f:bij(A,range(f))  *)
   477 Goal
   477 Goal
   478     "!!f g. [| f: bij(A,B);  g: bij(C,D);  A Int C = 0;  B Int D = 0 |] ==> \
   478     "[| f: bij(A,B);  g: bij(C,D);  A Int C = 0;  B Int D = 0 |] ==> \
   479 \           (f Un g) : bij(A Un C, B Un D)";
   479 \           (f Un g) : bij(A Un C, B Un D)";
   480 by (rtac invertible_imp_bijective 1);
   480 by (rtac invertible_imp_bijective 1);
   481 by (stac converse_Un 1);
   481 by (stac converse_Un 1);
   482 by (REPEAT (ares_tac [fun_disjoint_Un, bij_is_fun, bij_converse_bij] 1));
   482 by (REPEAT (ares_tac [fun_disjoint_Un, bij_is_fun, bij_converse_bij] 1));
   483 qed "bij_disjoint_Un";
   483 qed "bij_disjoint_Un";
   498      ORELSE ares_tac [subsetI,lamI,imageI] 2));
   498      ORELSE ares_tac [subsetI,lamI,imageI] 2));
   499 by (REPEAT (ares_tac [image_mono,restrict_subset,subset_refl] 1));
   499 by (REPEAT (ares_tac [image_mono,restrict_subset,subset_refl] 1));
   500 qed "restrict_image";
   500 qed "restrict_image";
   501 
   501 
   502 Goalw [inj_def]
   502 Goalw [inj_def]
   503     "!!f. [| f: inj(A,B);  C<=A |] ==> restrict(f,C): inj(C,B)";
   503     "[| f: inj(A,B);  C<=A |] ==> restrict(f,C): inj(C,B)";
   504 by (safe_tac (claset() addSEs [restrict_type2]));
   504 by (safe_tac (claset() addSEs [restrict_type2]));
   505 by (REPEAT (eresolve_tac [asm_rl, bspec RS bspec RS mp, subsetD,
   505 by (REPEAT (eresolve_tac [asm_rl, bspec RS bspec RS mp, subsetD,
   506                           box_equals, restrict] 1));
   506                           box_equals, restrict] 1));
   507 qed "restrict_inj";
   507 qed "restrict_inj";
   508 
   508 
   512 by (rtac (restrict_type2 RS surj_image) 3);
   512 by (rtac (restrict_type2 RS surj_image) 3);
   513 by (REPEAT (resolve_tac prems 1));
   513 by (REPEAT (resolve_tac prems 1));
   514 qed "restrict_surj";
   514 qed "restrict_surj";
   515 
   515 
   516 Goalw [inj_def,bij_def]
   516 Goalw [inj_def,bij_def]
   517     "!!f. [| f: inj(A,B);  C<=A |] ==> restrict(f,C): bij(C, f``C)";
   517     "[| f: inj(A,B);  C<=A |] ==> restrict(f,C): bij(C, f``C)";
   518 by (blast_tac (claset() addSIs [restrict, restrict_surj]
   518 by (blast_tac (claset() addSIs [restrict, restrict_surj]
   519 		       addIs [box_equals, surj_is_fun]) 1);
   519 		       addIs [box_equals, surj_is_fun]) 1);
   520 qed "restrict_bij";
   520 qed "restrict_bij";
   521 
   521 
   522 
   522 
   535 by (fast_tac (claset() addEs [range_type, mem_irrefl] 
   535 by (fast_tac (claset() addEs [range_type, mem_irrefl] 
   536 	              addDs [apply_equality]) 1);
   536 	              addDs [apply_equality]) 1);
   537 qed "inj_succ_restrict";
   537 qed "inj_succ_restrict";
   538 
   538 
   539 Goalw [inj_def]
   539 Goalw [inj_def]
   540     "!!f. [| f: inj(A,B);  a~:A;  b~:B |]  ==> \
   540     "[| f: inj(A,B);  a~:A;  b~:B |]  ==> \
   541 \         cons(<a,b>,f) : inj(cons(a,A), cons(b,B))";
   541 \         cons(<a,b>,f) : inj(cons(a,A), cons(b,B))";
   542 by (fast_tac (claset() addIs [apply_type]
   542 by (fast_tac (claset() addIs [apply_type]
   543                addss (simpset() addsimps [fun_extend, fun_extend_apply2,
   543                addss (simpset() addsimps [fun_extend, fun_extend_apply2,
   544 						fun_extend_apply1])) 1);
   544 						fun_extend_apply1])) 1);
   545 qed "inj_extend";
   545 qed "inj_extend";