src/ZF/Constructible/WFrec.thy
author wenzelm
Mon Jul 29 00:57:16 2002 +0200 (2002-07-29)
changeset 13428 99e52e78eb65
parent 13382 b37764a46b16
child 13505 52a16cb7fefb
permissions -rw-r--r--
eliminate open locales and special ML code;
paulson@13306
     1
header{*Relativized Well-Founded Recursion*}
paulson@13306
     2
paulson@13223
     3
theory WFrec = Wellorderings:
paulson@13223
     4
paulson@13223
     5
paulson@13254
     6
(*Many of these might be useful in WF.thy*)
paulson@13223
     7
paulson@13269
     8
lemma apply_recfun2:
paulson@13269
     9
    "[| is_recfun(r,a,H,f); <x,i>:f |] ==> i = H(x, restrict(f,r-``{x}))"
paulson@13269
    10
apply (frule apply_recfun) 
paulson@13269
    11
 apply (blast dest: is_recfun_type fun_is_rel) 
paulson@13269
    12
apply (simp add: function_apply_equality [OF _ is_recfun_imp_function])
paulson@13223
    13
done
paulson@13223
    14
paulson@13223
    15
text{*Expresses @{text is_recfun} as a recursion equation*}
paulson@13223
    16
lemma is_recfun_iff_equation:
paulson@13223
    17
     "is_recfun(r,a,H,f) <->
paulson@13223
    18
	   f \<in> r -`` {a} \<rightarrow> range(f) &
paulson@13223
    19
	   (\<forall>x \<in> r-``{a}. f`x = H(x, restrict(f, r-``{x})))"  
paulson@13223
    20
apply (rule iffI) 
paulson@13223
    21
 apply (simp add: is_recfun_type apply_recfun Ball_def vimage_singleton_iff, 
paulson@13223
    22
        clarify)  
paulson@13223
    23
apply (simp add: is_recfun_def) 
paulson@13223
    24
apply (rule fun_extension) 
paulson@13223
    25
  apply assumption
paulson@13223
    26
 apply (fast intro: lam_type, simp) 
paulson@13223
    27
done
paulson@13223
    28
paulson@13245
    29
lemma is_recfun_imp_in_r: "[|is_recfun(r,a,H,f); \<langle>x,i\<rangle> \<in> f|] ==> \<langle>x, a\<rangle> \<in> r"
paulson@13269
    30
by (blast dest: is_recfun_type fun_is_rel)
paulson@13245
    31
paulson@13254
    32
lemma trans_Int_eq:
paulson@13254
    33
      "[| trans(r); <y,x> \<in> r |] ==> r -`` {x} \<inter> r -`` {y} = r -`` {y}"
paulson@13251
    34
by (blast intro: transD) 
paulson@13223
    35
paulson@13254
    36
lemma is_recfun_restrict_idem:
paulson@13254
    37
     "is_recfun(r,a,H,f) ==> restrict(f, r -`` {a}) = f"
paulson@13254
    38
apply (drule is_recfun_type)
paulson@13254
    39
apply (auto simp add: Pi_iff subset_Sigma_imp_relation restrict_idem)  
paulson@13254
    40
done
paulson@13254
    41
paulson@13254
    42
lemma is_recfun_cong_lemma:
paulson@13254
    43
  "[| is_recfun(r,a,H,f); r = r'; a = a'; f = f'; 
paulson@13254
    44
      !!x g. [| <x,a'> \<in> r'; relation(g); domain(g) <= r' -``{x} |] 
paulson@13254
    45
             ==> H(x,g) = H'(x,g) |]
paulson@13254
    46
   ==> is_recfun(r',a',H',f')"
paulson@13254
    47
apply (simp add: is_recfun_def) 
paulson@13254
    48
apply (erule trans) 
paulson@13254
    49
apply (rule lam_cong) 
paulson@13254
    50
apply (simp_all add: vimage_singleton_iff Int_lower2)  
paulson@13254
    51
done
paulson@13254
    52
paulson@13254
    53
text{*For @{text is_recfun} we need only pay attention to functions
paulson@13254
    54
      whose domains are initial segments of @{term r}.*}
paulson@13254
    55
lemma is_recfun_cong:
paulson@13254
    56
  "[| r = r'; a = a'; f = f'; 
paulson@13254
    57
      !!x g. [| <x,a'> \<in> r'; relation(g); domain(g) <= r' -``{x} |] 
paulson@13254
    58
             ==> H(x,g) = H'(x,g) |]
paulson@13254
    59
   ==> is_recfun(r,a,H,f) <-> is_recfun(r',a',H',f')"
paulson@13254
    60
apply (rule iffI)
paulson@13254
    61
txt{*Messy: fast and blast don't work for some reason*}
paulson@13254
    62
apply (erule is_recfun_cong_lemma, auto) 
paulson@13254
    63
apply (erule is_recfun_cong_lemma)
paulson@13254
    64
apply (blast intro: sym)+
paulson@13254
    65
done
paulson@13223
    66
paulson@13319
    67
lemma (in M_axioms) is_recfun_separation':
paulson@13319
    68
    "[| f \<in> r -`` {a} \<rightarrow> range(f); g \<in> r -`` {b} \<rightarrow> range(g);
paulson@13319
    69
        M(r); M(f); M(g); M(a); M(b) |] 
paulson@13319
    70
     ==> separation(M, \<lambda>x. \<not> (\<langle>x, a\<rangle> \<in> r \<longrightarrow> \<langle>x, b\<rangle> \<in> r \<longrightarrow> f ` x = g ` x))"
paulson@13319
    71
apply (insert is_recfun_separation [of r f g a b]) 
paulson@13352
    72
apply (simp add: vimage_singleton_iff)
paulson@13319
    73
done
paulson@13223
    74
paulson@13251
    75
text{*Stated using @{term "trans(r)"} rather than
paulson@13223
    76
      @{term "transitive_rel(M,A,r)"} because the latter rewrites to
paulson@13223
    77
      the former anyway, by @{text transitive_rel_abs}.
paulson@13251
    78
      As always, theorems should be expressed in simplified form.
paulson@13251
    79
      The last three M-premises are redundant because of @{term "M(r)"}, 
paulson@13251
    80
      but without them we'd have to undertake
paulson@13251
    81
      more work to set up the induction formula.*}
paulson@13223
    82
lemma (in M_axioms) is_recfun_equal [rule_format]: 
paulson@13223
    83
    "[|is_recfun(r,a,H,f);  is_recfun(r,b,H,g);  
paulson@13251
    84
       wellfounded(M,r);  trans(r);
paulson@13251
    85
       M(f); M(g); M(r); M(x); M(a); M(b) |] 
paulson@13223
    86
     ==> <x,a> \<in> r --> <x,b> \<in> r --> f`x=g`x"
paulson@13339
    87
apply (frule_tac f=f in is_recfun_type) 
paulson@13339
    88
apply (frule_tac f=g in is_recfun_type) 
paulson@13223
    89
apply (simp add: is_recfun_def)
paulson@13254
    90
apply (erule_tac a=x in wellfounded_induct, assumption+)
paulson@13251
    91
txt{*Separation to justify the induction*}
paulson@13319
    92
 apply (blast intro: is_recfun_separation') 
paulson@13251
    93
txt{*Now the inductive argument itself*}
paulson@13254
    94
apply clarify 
paulson@13223
    95
apply (erule ssubst)+
paulson@13223
    96
apply (simp (no_asm_simp) add: vimage_singleton_iff restrict_def)
paulson@13223
    97
apply (rename_tac x1)
paulson@13223
    98
apply (rule_tac t="%z. H(x1,z)" in subst_context) 
paulson@13223
    99
apply (subgoal_tac "ALL y : r-``{x1}. ALL z. <y,z>:f <-> <y,z>:g")
paulson@13251
   100
 apply (blast intro: transD) 
paulson@13223
   101
apply (simp add: apply_iff) 
paulson@13251
   102
apply (blast intro: transD sym) 
paulson@13223
   103
done
paulson@13223
   104
paulson@13223
   105
lemma (in M_axioms) is_recfun_cut: 
paulson@13223
   106
    "[|is_recfun(r,a,H,f);  is_recfun(r,b,H,g);  
paulson@13251
   107
       wellfounded(M,r); trans(r); 
paulson@13251
   108
       M(f); M(g); M(r); <b,a> \<in> r |]   
paulson@13223
   109
      ==> restrict(f, r-``{b}) = g"
paulson@13339
   110
apply (frule_tac f=f in is_recfun_type) 
paulson@13223
   111
apply (rule fun_extension) 
paulson@13251
   112
apply (blast intro: transD restrict_type2) 
paulson@13223
   113
apply (erule is_recfun_type, simp) 
paulson@13251
   114
apply (blast intro: is_recfun_equal transD dest: transM) 
paulson@13223
   115
done
paulson@13223
   116
paulson@13223
   117
lemma (in M_axioms) is_recfun_functional:
paulson@13223
   118
     "[|is_recfun(r,a,H,f);  is_recfun(r,a,H,g);  
paulson@13268
   119
       wellfounded(M,r); trans(r); M(f); M(g); M(r) |] ==> f=g"
paulson@13223
   120
apply (rule fun_extension)
paulson@13223
   121
apply (erule is_recfun_type)+
paulson@13251
   122
apply (blast intro!: is_recfun_equal dest: transM) 
paulson@13254
   123
done 
paulson@13223
   124
wenzelm@13295
   125
text{*Tells us that @{text is_recfun} can (in principle) be relativized.*}
paulson@13223
   126
lemma (in M_axioms) is_recfun_relativize:
paulson@13254
   127
  "[| M(r); M(f); \<forall>x[M]. \<forall>g[M]. function(g) --> M(H(x,g)) |] 
paulson@13251
   128
   ==> is_recfun(r,a,H,f) <->
paulson@13254
   129
       (\<forall>z[M]. z \<in> f <-> 
paulson@13254
   130
        (\<exists>x[M]. <x,a> \<in> r & z = <x, H(x, restrict(f, r-``{x}))>))";
paulson@13254
   131
apply (simp add: is_recfun_def lam_def)
paulson@13223
   132
apply (safe intro!: equalityI) 
paulson@13254
   133
   apply (drule equalityD1 [THEN subsetD], assumption) 
paulson@13254
   134
   apply (blast dest: pair_components_in_M) 
paulson@13254
   135
  apply (blast elim!: equalityE dest: pair_components_in_M)
paulson@13254
   136
 apply (frule transM, assumption, rotate_tac -1) 
paulson@13223
   137
 apply simp  
paulson@13223
   138
 apply blast
paulson@13254
   139
apply (subgoal_tac "is_function(M,f)")
paulson@13254
   140
 txt{*We use @{term "is_function"} rather than @{term "function"} because
paulson@13254
   141
      the subgoal's easier to prove with relativized quantifiers!*}
paulson@13254
   142
 prefer 2 apply (simp add: is_function_def) 
paulson@13223
   143
apply (frule pair_components_in_M, assumption) 
paulson@13254
   144
apply (simp add: is_recfun_imp_function function_restrictI) 
paulson@13223
   145
done
paulson@13223
   146
paulson@13223
   147
(* ideas for further weaking the H-closure premise:
paulson@13223
   148
apply (drule spec [THEN spec]) 
paulson@13223
   149
apply (erule mp)
paulson@13223
   150
apply (intro conjI)
paulson@13223
   151
apply (blast dest!: pair_components_in_M)
paulson@13223
   152
apply (blast intro!: function_restrictI dest!: pair_components_in_M)
paulson@13223
   153
apply (blast intro!: function_restrictI dest!: pair_components_in_M)
paulson@13223
   154
apply (simp only: subset_iff domain_iff restrict_iff vimage_iff) 
paulson@13269
   155
apply (simp add: vimage_singleton_iff) 
paulson@13223
   156
apply (intro allI impI conjI)
paulson@13223
   157
apply (blast intro: transM dest!: pair_components_in_M)
paulson@13223
   158
prefer 4;apply blast 
paulson@13223
   159
*)
paulson@13223
   160
paulson@13223
   161
lemma (in M_axioms) is_recfun_restrict:
paulson@13251
   162
     "[| wellfounded(M,r); trans(r); is_recfun(r,x,H,f); \<langle>y,x\<rangle> \<in> r; 
paulson@13251
   163
       M(r); M(f); 
paulson@13254
   164
       \<forall>x[M]. \<forall>g[M]. function(g) --> M(H(x,g)) |]
paulson@13223
   165
       ==> is_recfun(r, y, H, restrict(f, r -`` {y}))"
paulson@13223
   166
apply (frule pair_components_in_M, assumption, clarify) 
paulson@13254
   167
apply (simp (no_asm_simp) add: is_recfun_relativize restrict_iff
paulson@13254
   168
           trans_Int_eq)
paulson@13223
   169
apply safe
paulson@13223
   170
  apply (simp_all add: vimage_singleton_iff is_recfun_type [THEN apply_iff]) 
paulson@13223
   171
  apply (frule_tac x=xa in pair_components_in_M, assumption)
paulson@13251
   172
  apply (frule_tac x=xa in apply_recfun, blast intro: transD)  
paulson@13247
   173
  apply (simp add: is_recfun_type [THEN apply_iff] 
paulson@13251
   174
                   is_recfun_imp_function function_restrictI)
paulson@13251
   175
apply (blast intro: apply_recfun dest: transD)
paulson@13223
   176
done
paulson@13223
   177
 
paulson@13223
   178
lemma (in M_axioms) restrict_Y_lemma:
paulson@13251
   179
   "[| wellfounded(M,r); trans(r); M(r);
paulson@13254
   180
       \<forall>x[M]. \<forall>g[M]. function(g) --> M(H(x,g));  M(Y);
paulson@13299
   181
       \<forall>b[M]. 
paulson@13223
   182
	   b \<in> Y <->
paulson@13299
   183
	   (\<exists>x[M]. <x,a1> \<in> r &
paulson@13299
   184
            (\<exists>y[M]. b = \<langle>x,y\<rangle> & (\<exists>g[M]. is_recfun(r,x,H,g) \<and> y = H(x,g))));
paulson@13299
   185
          \<langle>x,a1\<rangle> \<in> r; is_recfun(r,x,H,f); M(f) |]
paulson@13223
   186
       ==> restrict(Y, r -`` {x}) = f"
paulson@13251
   187
apply (subgoal_tac "\<forall>y \<in> r-``{x}. \<forall>z. <y,z>:Y <-> <y,z>:f") 
paulson@13251
   188
 apply (simp (no_asm_simp) add: restrict_def) 
paulson@13254
   189
 apply (thin_tac "rall(M,?P)")+  --{*essential for efficiency*}
paulson@13251
   190
 apply (frule is_recfun_type [THEN fun_is_rel], blast)
paulson@13223
   191
apply (frule pair_components_in_M, assumption, clarify) 
paulson@13223
   192
apply (rule iffI)
paulson@13223
   193
 apply (frule_tac y="<y,z>" in transM, assumption )
paulson@13223
   194
 apply (rotate_tac -1)   
paulson@13223
   195
 apply (clarsimp simp add: vimage_singleton_iff is_recfun_type [THEN apply_iff]
paulson@13223
   196
			   apply_recfun is_recfun_cut) 
paulson@13223
   197
txt{*Opposite inclusion: something in f, show in Y*}
paulson@13293
   198
apply (frule_tac y="<y,z>" in transM, assumption)  
paulson@13293
   199
apply (simp add: vimage_singleton_iff) 
paulson@13293
   200
apply (rule conjI) 
paulson@13293
   201
 apply (blast dest: transD) 
paulson@13268
   202
apply (rule_tac x="restrict(f, r -`` {y})" in rexI) 
paulson@13268
   203
apply (simp_all add: is_recfun_restrict
paulson@13268
   204
                     apply_recfun is_recfun_type [THEN apply_iff]) 
paulson@13223
   205
done
paulson@13223
   206
paulson@13245
   207
text{*For typical applications of Replacement for recursive definitions*}
paulson@13245
   208
lemma (in M_axioms) univalent_is_recfun:
paulson@13251
   209
     "[|wellfounded(M,r); trans(r); M(r)|]
paulson@13268
   210
      ==> univalent (M, A, \<lambda>x p. 
paulson@13293
   211
              \<exists>y[M]. p = \<langle>x,y\<rangle> & (\<exists>f[M]. is_recfun(r,x,H,f) & y = H(x,f)))"
paulson@13245
   212
apply (simp add: univalent_def) 
paulson@13245
   213
apply (blast dest: is_recfun_functional) 
paulson@13245
   214
done
paulson@13245
   215
paulson@13299
   216
paulson@13223
   217
text{*Proof of the inductive step for @{text exists_is_recfun}, since
paulson@13223
   218
      we must prove two versions.*}
paulson@13223
   219
lemma (in M_axioms) exists_is_recfun_indstep:
paulson@13268
   220
    "[|\<forall>y. \<langle>y, a1\<rangle> \<in> r --> (\<exists>f[M]. is_recfun(r, y, H, f)); 
paulson@13251
   221
       wellfounded(M,r); trans(r); M(r); M(a1);
paulson@13268
   222
       strong_replacement(M, \<lambda>x z. 
paulson@13268
   223
              \<exists>y[M]. \<exists>g[M]. pair(M,x,y,z) & is_recfun(r,x,H,g) & y = H(x,g)); 
paulson@13254
   224
       \<forall>x[M]. \<forall>g[M]. function(g) --> M(H(x,g))|]   
paulson@13268
   225
      ==> \<exists>f[M]. is_recfun(r,a1,H,f)"
paulson@13223
   226
apply (drule_tac A="r-``{a1}" in strong_replacementD)
paulson@13251
   227
  apply blast 
paulson@13223
   228
 txt{*Discharge the "univalent" obligation of Replacement*}
paulson@13251
   229
 apply (simp add: univalent_is_recfun) 
paulson@13223
   230
txt{*Show that the constructed object satisfies @{text is_recfun}*} 
paulson@13223
   231
apply clarify 
paulson@13268
   232
apply (rule_tac x=Y in rexI)  
paulson@13254
   233
txt{*Unfold only the top-level occurrence of @{term is_recfun}*}
paulson@13254
   234
apply (simp (no_asm_simp) add: is_recfun_relativize [of concl: _ a1])
paulson@13268
   235
txt{*The big iff-formula defining @{term Y} is now redundant*}
paulson@13254
   236
apply safe 
paulson@13299
   237
 apply (simp add: vimage_singleton_iff restrict_Y_lemma [of r H _ a1]) 
paulson@13223
   238
txt{*one more case*}
paulson@13254
   239
apply (simp (no_asm_simp) add: Bex_def vimage_singleton_iff)
paulson@13223
   240
apply (drule_tac x1=x in spec [THEN mp], assumption, clarify) 
paulson@13268
   241
apply (rename_tac f) 
paulson@13268
   242
apply (rule_tac x=f in rexI) 
paulson@13293
   243
apply (simp_all add: restrict_Y_lemma [of r H])
paulson@13299
   244
txt{*FIXME: should not be needed!*}
paulson@13299
   245
apply (subst restrict_Y_lemma [of r H])
paulson@13299
   246
apply (simp add: vimage_singleton_iff)+
paulson@13299
   247
apply blast+
paulson@13223
   248
done
paulson@13223
   249
paulson@13223
   250
text{*Relativized version, when we have the (currently weaker) premise
paulson@13251
   251
      @{term "wellfounded(M,r)"}*}
paulson@13223
   252
lemma (in M_axioms) wellfounded_exists_is_recfun:
paulson@13251
   253
    "[|wellfounded(M,r);  trans(r);  
paulson@13268
   254
       separation(M, \<lambda>x. ~ (\<exists>f[M]. is_recfun(r, x, H, f)));
paulson@13268
   255
       strong_replacement(M, \<lambda>x z. 
paulson@13268
   256
          \<exists>y[M]. \<exists>g[M]. pair(M,x,y,z) & is_recfun(r,x,H,g) & y = H(x,g)); 
paulson@13251
   257
       M(r);  M(a);  
paulson@13254
   258
       \<forall>x[M]. \<forall>g[M]. function(g) --> M(H(x,g)) |]   
paulson@13268
   259
      ==> \<exists>f[M]. is_recfun(r,a,H,f)"
paulson@13251
   260
apply (rule wellfounded_induct, assumption+, clarify)
paulson@13223
   261
apply (rule exists_is_recfun_indstep, assumption+)
paulson@13223
   262
done
paulson@13223
   263
paulson@13251
   264
lemma (in M_axioms) wf_exists_is_recfun [rule_format]:
paulson@13268
   265
    "[|wf(r);  trans(r);  M(r);  
paulson@13268
   266
       strong_replacement(M, \<lambda>x z. 
paulson@13268
   267
         \<exists>y[M]. \<exists>g[M]. pair(M,x,y,z) & is_recfun(r,x,H,g) & y = H(x,g)); 
paulson@13254
   268
       \<forall>x[M]. \<forall>g[M]. function(g) --> M(H(x,g)) |]   
paulson@13268
   269
      ==> M(a) --> (\<exists>f[M]. is_recfun(r,a,H,f))"
paulson@13251
   270
apply (rule wf_induct, assumption+)
paulson@13251
   271
apply (frule wf_imp_relativized)
paulson@13251
   272
apply (intro impI)
paulson@13268
   273
apply (rule exists_is_recfun_indstep) 
paulson@13268
   274
      apply (blast dest: transM del: rev_rallE, assumption+)
paulson@13223
   275
done
paulson@13223
   276
paulson@13223
   277
constdefs
paulson@13353
   278
  M_is_recfun :: "[i=>o, [i,i,i]=>o, i, i, i] => o"
paulson@13352
   279
   "M_is_recfun(M,MH,r,a,f) == 
paulson@13254
   280
     \<forall>z[M]. z \<in> f <-> 
paulson@13254
   281
            (\<exists>x[M]. \<exists>y[M]. \<exists>xa[M]. \<exists>sx[M]. \<exists>r_sx[M]. \<exists>f_r_sx[M]. 
paulson@13254
   282
	       pair(M,x,y,z) & pair(M,x,a,xa) & upair(M,x,x,sx) &
paulson@13254
   283
               pre_image(M,r,sx,r_sx) & restriction(M,f,r_sx,f_r_sx) &
paulson@13348
   284
               xa \<in> r & MH(x, f_r_sx, y))"
paulson@13223
   285
paulson@13353
   286
  is_wfrec :: "[i=>o, [i,i,i]=>o, i, i, i] => o"
paulson@13353
   287
   "is_wfrec(M,MH,r,a,z) == 
paulson@13353
   288
      \<exists>f[M]. M_is_recfun(M,MH,r,a,f) & MH(a,f,z)"
paulson@13353
   289
paulson@13353
   290
  wfrec_replacement :: "[i=>o, [i,i,i]=>o, i] => o"
paulson@13353
   291
   "wfrec_replacement(M,MH,r) ==
paulson@13353
   292
        strong_replacement(M, 
paulson@13353
   293
             \<lambda>x z. \<exists>y[M]. pair(M,x,y,z) & is_wfrec(M,MH,r,x,y))"
paulson@13353
   294
paulson@13350
   295
lemma (in M_axioms) is_recfun_abs:
paulson@13350
   296
     "[| \<forall>x[M]. \<forall>g[M]. function(g) --> M(H(x,g));  M(r); M(a); M(f); 
paulson@13353
   297
         relativize2(M,MH,H) |] 
paulson@13352
   298
      ==> M_is_recfun(M,MH,r,a,f) <-> is_recfun(r,a,H,f)"
paulson@13353
   299
apply (simp add: M_is_recfun_def relativize2_def is_recfun_relativize)
paulson@13254
   300
apply (rule rall_cong)
paulson@13254
   301
apply (blast dest: transM)
paulson@13223
   302
done
paulson@13223
   303
paulson@13223
   304
lemma M_is_recfun_cong [cong]:
paulson@13223
   305
     "[| r = r'; a = a'; f = f'; 
paulson@13348
   306
       !!x g y. [| M(x); M(g); M(y) |] ==> MH(x,g,y) <-> MH'(x,g,y) |]
paulson@13352
   307
      ==> M_is_recfun(M,MH,r,a,f) <-> M_is_recfun(M,MH',r',a',f')"
paulson@13223
   308
by (simp add: M_is_recfun_def) 
paulson@13223
   309
paulson@13353
   310
lemma (in M_axioms) is_wfrec_abs:
paulson@13353
   311
     "[| \<forall>x[M]. \<forall>g[M]. function(g) --> M(H(x,g)); 
paulson@13353
   312
         relativize2(M,MH,H);  M(r); M(a); M(z) |]
paulson@13353
   313
      ==> is_wfrec(M,MH,r,a,z) <-> 
paulson@13353
   314
          (\<exists>g[M]. is_recfun(r,a,H,g) & z = H(a,g))"
paulson@13353
   315
by (simp add: is_wfrec_def relativize2_def is_recfun_abs)
paulson@13223
   316
paulson@13353
   317
text{*Relating @{term wfrec_replacement} to native constructs*}
paulson@13353
   318
lemma (in M_axioms) wfrec_replacement':
paulson@13353
   319
  "[|wfrec_replacement(M,MH,r);
paulson@13353
   320
     \<forall>x[M]. \<forall>g[M]. function(g) --> M(H(x,g)); 
paulson@13353
   321
     relativize2(M,MH,H);  M(r)|] 
paulson@13353
   322
   ==> strong_replacement(M, \<lambda>x z. \<exists>y[M]. 
paulson@13353
   323
                pair(M,x,y,z) & (\<exists>g[M]. is_recfun(r,x,H,g) & y = H(x,g)))"
paulson@13353
   324
apply (rotate_tac 1) 
paulson@13353
   325
apply (simp add: wfrec_replacement_def is_wfrec_abs) 
paulson@13353
   326
done
paulson@13353
   327
paulson@13353
   328
lemma wfrec_replacement_cong [cong]:
paulson@13353
   329
     "[| !!x y z. [| M(x); M(y); M(z) |] ==> MH(x,y,z) <-> MH'(x,y,z);
paulson@13353
   330
         r=r' |] 
paulson@13353
   331
      ==> wfrec_replacement(M, %x y. MH(x,y), r) <-> 
paulson@13353
   332
          wfrec_replacement(M, %x y. MH'(x,y), r')" 
paulson@13353
   333
by (simp add: is_wfrec_def wfrec_replacement_def) 
paulson@13353
   334
paulson@13353
   335
paulson@13353
   336
(*FIXME: update to use new techniques!!*)
paulson@13223
   337
constdefs
paulson@13350
   338
 (*This expresses ordinal addition in the language of ZF.  It also 
paulson@13223
   339
   provides an abbreviation that can be used in the instance of strong
paulson@13223
   340
   replacement below.  Here j is used to define the relation, namely
paulson@13223
   341
   Memrel(succ(j)), while x determines the domain of f.*)
paulson@13223
   342
 is_oadd_fun :: "[i=>o,i,i,i,i] => o"
paulson@13223
   343
    "is_oadd_fun(M,i,j,x,f) == 
paulson@13223
   344
       (\<forall>sj msj. M(sj) --> M(msj) --> 
paulson@13223
   345
                 successor(M,j,sj) --> membership(M,sj,msj) --> 
paulson@13352
   346
	         M_is_recfun(M, 
paulson@13348
   347
		     %x g y. \<exists>gx[M]. image(M,g,x,gx) & union(M,i,gx,y),
paulson@13352
   348
		     msj, x, f))"
paulson@13223
   349
paulson@13223
   350
 is_oadd :: "[i=>o,i,i,i] => o"
paulson@13223
   351
    "is_oadd(M,i,j,k) == 
paulson@13223
   352
        (~ ordinal(M,i) & ~ ordinal(M,j) & k=0) |
paulson@13223
   353
        (~ ordinal(M,i) & ordinal(M,j) & k=j) |
paulson@13223
   354
        (ordinal(M,i) & ~ ordinal(M,j) & k=i) |
paulson@13223
   355
        (ordinal(M,i) & ordinal(M,j) & 
paulson@13223
   356
	 (\<exists>f fj sj. M(f) & M(fj) & M(sj) & 
paulson@13223
   357
		    successor(M,j,sj) & is_oadd_fun(M,i,sj,sj,f) & 
paulson@13223
   358
		    fun_apply(M,f,j,fj) & fj = k))"
paulson@13223
   359
paulson@13223
   360
 (*NEEDS RELATIVIZATION*)
paulson@13223
   361
 omult_eqns :: "[i,i,i,i] => o"
paulson@13223
   362
    "omult_eqns(i,x,g,z) ==
paulson@13223
   363
            Ord(x) & 
paulson@13223
   364
	    (x=0 --> z=0) &
paulson@13223
   365
            (\<forall>j. x = succ(j) --> z = g`j ++ i) &
paulson@13223
   366
            (Limit(x) --> z = \<Union>(g``x))"
paulson@13223
   367
paulson@13223
   368
 is_omult_fun :: "[i=>o,i,i,i] => o"
paulson@13223
   369
    "is_omult_fun(M,i,j,f) == 
paulson@13223
   370
	    (\<exists>df. M(df) & is_function(M,f) & 
paulson@13223
   371
                  is_domain(M,f,df) & subset(M, j, df)) & 
paulson@13223
   372
            (\<forall>x\<in>j. omult_eqns(i,x,f,f`x))"
paulson@13223
   373
paulson@13223
   374
 is_omult :: "[i=>o,i,i,i] => o"
paulson@13223
   375
    "is_omult(M,i,j,k) == 
paulson@13223
   376
	\<exists>f fj sj. M(f) & M(fj) & M(sj) & 
paulson@13223
   377
                  successor(M,j,sj) & is_omult_fun(M,i,sj,f) & 
paulson@13223
   378
                  fun_apply(M,f,j,fj) & fj = k"
paulson@13223
   379
paulson@13223
   380
wenzelm@13428
   381
locale M_ord_arith = M_axioms +
paulson@13223
   382
  assumes oadd_strong_replacement:
paulson@13223
   383
   "[| M(i); M(j) |] ==>
paulson@13223
   384
    strong_replacement(M, 
paulson@13293
   385
         \<lambda>x z. \<exists>y[M]. pair(M,x,y,z) & 
paulson@13293
   386
                  (\<exists>f[M]. \<exists>fx[M]. is_oadd_fun(M,i,j,x,f) & 
paulson@13293
   387
		           image(M,f,x,fx) & y = i Un fx))"
paulson@13293
   388
paulson@13223
   389
 and omult_strong_replacement':
paulson@13223
   390
   "[| M(i); M(j) |] ==>
paulson@13293
   391
    strong_replacement(M, 
paulson@13293
   392
         \<lambda>x z. \<exists>y[M]. z = <x,y> &
paulson@13293
   393
	     (\<exists>g[M]. is_recfun(Memrel(succ(j)),x,%x g. THE z. omult_eqns(i,x,g,z),g) & 
paulson@13293
   394
	     y = (THE z. omult_eqns(i, x, g, z))))" 
paulson@13223
   395
paulson@13223
   396
paulson@13223
   397
wenzelm@13295
   398
text{*@{text is_oadd_fun}: Relating the pure "language of set theory" to Isabelle/ZF*}
paulson@13268
   399
lemma (in M_ord_arith) is_oadd_fun_iff:
paulson@13223
   400
   "[| a\<le>j; M(i); M(j); M(a); M(f) |] 
paulson@13223
   401
    ==> is_oadd_fun(M,i,j,a,f) <->
paulson@13223
   402
	f \<in> a \<rightarrow> range(f) & (\<forall>x. M(x) --> x < a --> f`x = i Un f``x)"
paulson@13223
   403
apply (frule lt_Ord) 
paulson@13223
   404
apply (simp add: is_oadd_fun_def Memrel_closed Un_closed 
paulson@13353
   405
             relativize2_def is_recfun_abs [of "%x g. i Un g``x"]
paulson@13223
   406
             image_closed is_recfun_iff_equation  
paulson@13223
   407
             Ball_def lt_trans [OF ltI, of _ a] lt_Memrel)
paulson@13223
   408
apply (simp add: lt_def) 
paulson@13223
   409
apply (blast dest: transM) 
paulson@13223
   410
done
paulson@13223
   411
paulson@13223
   412
paulson@13268
   413
lemma (in M_ord_arith) oadd_strong_replacement':
paulson@13223
   414
    "[| M(i); M(j) |] ==>
paulson@13293
   415
     strong_replacement(M, 
paulson@13293
   416
            \<lambda>x z. \<exists>y[M]. z = <x,y> &
paulson@13293
   417
		  (\<exists>g[M]. is_recfun(Memrel(succ(j)),x,%x g. i Un g``x,g) & 
paulson@13293
   418
		  y = i Un g``x))" 
paulson@13223
   419
apply (insert oadd_strong_replacement [of i j]) 
paulson@13353
   420
apply (simp add: is_oadd_fun_def relativize2_def is_recfun_abs [of "%x g. i Un g``x"])  
paulson@13223
   421
done
paulson@13223
   422
paulson@13223
   423
paulson@13268
   424
lemma (in M_ord_arith) exists_oadd:
paulson@13223
   425
    "[| Ord(j);  M(i);  M(j) |]
paulson@13268
   426
     ==> \<exists>f[M]. is_recfun(Memrel(succ(j)), j, %x g. i Un g``x, f)"
paulson@13251
   427
apply (rule wf_exists_is_recfun [OF wf_Memrel trans_Memrel])
paulson@13268
   428
    apply (simp_all add: Memrel_type oadd_strong_replacement') 
paulson@13268
   429
done 
paulson@13268
   430
paulson@13268
   431
lemma (in M_ord_arith) exists_oadd_fun:
paulson@13268
   432
    "[| Ord(j);  M(i);  M(j) |] ==> \<exists>f[M]. is_oadd_fun(M,i,succ(j),succ(j),f)"
paulson@13268
   433
apply (rule exists_oadd [THEN rexE])
paulson@13268
   434
apply (erule Ord_succ, assumption, simp) 
paulson@13268
   435
apply (rename_tac f) 
paulson@13268
   436
apply (frule is_recfun_type)
paulson@13268
   437
apply (rule_tac x=f in rexI) 
paulson@13268
   438
 apply (simp add: fun_is_function domain_of_fun lt_Memrel apply_recfun lt_def
paulson@13268
   439
                  is_oadd_fun_iff Ord_trans [OF _ succI1], assumption)
paulson@13223
   440
done
paulson@13223
   441
paulson@13268
   442
lemma (in M_ord_arith) is_oadd_fun_apply:
paulson@13223
   443
    "[| x < j; M(i); M(j); M(f); is_oadd_fun(M,i,j,j,f) |] 
paulson@13223
   444
     ==> f`x = i Un (\<Union>k\<in>x. {f ` k})"
paulson@13223
   445
apply (simp add: is_oadd_fun_iff lt_Ord2, clarify) 
paulson@13223
   446
apply (frule lt_closed, simp)
paulson@13223
   447
apply (frule leI [THEN le_imp_subset])  
paulson@13223
   448
apply (simp add: image_fun, blast) 
paulson@13223
   449
done
paulson@13223
   450
paulson@13268
   451
lemma (in M_ord_arith) is_oadd_fun_iff_oadd [rule_format]:
paulson@13223
   452
    "[| is_oadd_fun(M,i,J,J,f); M(i); M(J); M(f); Ord(i); Ord(j) |] 
paulson@13223
   453
     ==> j<J --> f`j = i++j"
paulson@13223
   454
apply (erule_tac i=j in trans_induct, clarify) 
paulson@13223
   455
apply (subgoal_tac "\<forall>k\<in>x. k<J")
paulson@13223
   456
 apply (simp (no_asm_simp) add: is_oadd_def oadd_unfold is_oadd_fun_apply)
paulson@13223
   457
apply (blast intro: lt_trans ltI lt_Ord) 
paulson@13223
   458
done
paulson@13223
   459
paulson@13268
   460
lemma (in M_ord_arith) Ord_oadd_abs:
paulson@13223
   461
    "[| M(i); M(j); M(k); Ord(i); Ord(j) |] ==> is_oadd(M,i,j,k) <-> k = i++j"
paulson@13352
   462
apply (simp add: is_oadd_def is_oadd_fun_iff_oadd)
paulson@13223
   463
apply (frule exists_oadd_fun [of j i], blast+)
paulson@13223
   464
done
paulson@13223
   465
paulson@13268
   466
lemma (in M_ord_arith) oadd_abs:
paulson@13223
   467
    "[| M(i); M(j); M(k) |] ==> is_oadd(M,i,j,k) <-> k = i++j"
paulson@13223
   468
apply (case_tac "Ord(i) & Ord(j)")
paulson@13223
   469
 apply (simp add: Ord_oadd_abs)
paulson@13223
   470
apply (auto simp add: is_oadd_def oadd_eq_if_raw_oadd)
paulson@13223
   471
done
paulson@13223
   472
paulson@13268
   473
lemma (in M_ord_arith) oadd_closed [intro,simp]:
paulson@13223
   474
    "[| M(i); M(j) |] ==> M(i++j)"
paulson@13223
   475
apply (simp add: oadd_eq_if_raw_oadd, clarify) 
paulson@13223
   476
apply (simp add: raw_oadd_eq_oadd) 
paulson@13223
   477
apply (frule exists_oadd_fun [of j i], auto)
paulson@13223
   478
apply (simp add: apply_closed is_oadd_fun_iff_oadd [symmetric]) 
paulson@13223
   479
done
paulson@13223
   480
paulson@13223
   481
paulson@13223
   482
text{*Ordinal Multiplication*}
paulson@13223
   483
paulson@13223
   484
lemma omult_eqns_unique:
paulson@13223
   485
     "[| omult_eqns(i,x,g,z); omult_eqns(i,x,g,z') |] ==> z=z'";
paulson@13223
   486
apply (simp add: omult_eqns_def, clarify) 
paulson@13223
   487
apply (erule Ord_cases, simp_all) 
paulson@13223
   488
done
paulson@13223
   489
paulson@13223
   490
lemma omult_eqns_0: "omult_eqns(i,0,g,z) <-> z=0"
paulson@13223
   491
by (simp add: omult_eqns_def)
paulson@13223
   492
paulson@13223
   493
lemma the_omult_eqns_0: "(THE z. omult_eqns(i,0,g,z)) = 0"
paulson@13223
   494
by (simp add: omult_eqns_0)
paulson@13223
   495
paulson@13223
   496
lemma omult_eqns_succ: "omult_eqns(i,succ(j),g,z) <-> Ord(j) & z = g`j ++ i"
paulson@13223
   497
by (simp add: omult_eqns_def)
paulson@13223
   498
paulson@13223
   499
lemma the_omult_eqns_succ:
paulson@13223
   500
     "Ord(j) ==> (THE z. omult_eqns(i,succ(j),g,z)) = g`j ++ i"
paulson@13223
   501
by (simp add: omult_eqns_succ) 
paulson@13223
   502
paulson@13223
   503
lemma omult_eqns_Limit:
paulson@13223
   504
     "Limit(x) ==> omult_eqns(i,x,g,z) <-> z = \<Union>(g``x)"
paulson@13223
   505
apply (simp add: omult_eqns_def) 
paulson@13223
   506
apply (blast intro: Limit_is_Ord) 
paulson@13223
   507
done
paulson@13223
   508
paulson@13223
   509
lemma the_omult_eqns_Limit:
paulson@13223
   510
     "Limit(x) ==> (THE z. omult_eqns(i,x,g,z)) = \<Union>(g``x)"
paulson@13223
   511
by (simp add: omult_eqns_Limit)
paulson@13223
   512
paulson@13223
   513
lemma omult_eqns_Not: "~ Ord(x) ==> ~ omult_eqns(i,x,g,z)"
paulson@13223
   514
by (simp add: omult_eqns_def)
paulson@13223
   515
paulson@13223
   516
paulson@13268
   517
lemma (in M_ord_arith) the_omult_eqns_closed:
paulson@13223
   518
    "[| M(i); M(x); M(g); function(g) |] 
paulson@13223
   519
     ==> M(THE z. omult_eqns(i, x, g, z))"
paulson@13223
   520
apply (case_tac "Ord(x)")
paulson@13223
   521
 prefer 2 apply (simp add: omult_eqns_Not) --{*trivial, non-Ord case*}
paulson@13223
   522
apply (erule Ord_cases) 
paulson@13223
   523
  apply (simp add: omult_eqns_0)
paulson@13223
   524
 apply (simp add: omult_eqns_succ apply_closed oadd_closed) 
paulson@13223
   525
apply (simp add: omult_eqns_Limit) 
paulson@13223
   526
done
paulson@13223
   527
paulson@13268
   528
lemma (in M_ord_arith) exists_omult:
paulson@13223
   529
    "[| Ord(j);  M(i);  M(j) |]
paulson@13268
   530
     ==> \<exists>f[M]. is_recfun(Memrel(succ(j)), j, %x g. THE z. omult_eqns(i,x,g,z), f)"
paulson@13251
   531
apply (rule wf_exists_is_recfun [OF wf_Memrel trans_Memrel])
paulson@13268
   532
    apply (simp_all add: Memrel_type omult_strong_replacement') 
paulson@13223
   533
apply (blast intro: the_omult_eqns_closed) 
paulson@13223
   534
done
paulson@13223
   535
paulson@13268
   536
lemma (in M_ord_arith) exists_omult_fun:
paulson@13268
   537
    "[| Ord(j);  M(i);  M(j) |] ==> \<exists>f[M]. is_omult_fun(M,i,succ(j),f)"
paulson@13268
   538
apply (rule exists_omult [THEN rexE])
paulson@13223
   539
apply (erule Ord_succ, assumption, simp) 
paulson@13268
   540
apply (rename_tac f) 
paulson@13223
   541
apply (frule is_recfun_type)
paulson@13268
   542
apply (rule_tac x=f in rexI) 
paulson@13223
   543
apply (simp add: fun_is_function domain_of_fun lt_Memrel apply_recfun lt_def
paulson@13223
   544
                 is_omult_fun_def Ord_trans [OF _ succI1])
paulson@13268
   545
 apply (force dest: Ord_in_Ord' 
paulson@13268
   546
              simp add: omult_eqns_def the_omult_eqns_0 the_omult_eqns_succ
paulson@13268
   547
                        the_omult_eqns_Limit, assumption)
paulson@13223
   548
done
paulson@13223
   549
paulson@13268
   550
lemma (in M_ord_arith) is_omult_fun_apply_0:
paulson@13223
   551
    "[| 0 < j; is_omult_fun(M,i,j,f) |] ==> f`0 = 0"
paulson@13223
   552
by (simp add: is_omult_fun_def omult_eqns_def lt_def ball_conj_distrib)
paulson@13223
   553
paulson@13268
   554
lemma (in M_ord_arith) is_omult_fun_apply_succ:
paulson@13223
   555
    "[| succ(x) < j; is_omult_fun(M,i,j,f) |] ==> f`succ(x) = f`x ++ i"
paulson@13223
   556
by (simp add: is_omult_fun_def omult_eqns_def lt_def, blast) 
paulson@13223
   557
paulson@13268
   558
lemma (in M_ord_arith) is_omult_fun_apply_Limit:
paulson@13223
   559
    "[| x < j; Limit(x); M(j); M(f); is_omult_fun(M,i,j,f) |] 
paulson@13223
   560
     ==> f ` x = (\<Union>y\<in>x. f`y)"
paulson@13223
   561
apply (simp add: is_omult_fun_def omult_eqns_def domain_closed lt_def, clarify)
paulson@13223
   562
apply (drule subset_trans [OF OrdmemD], assumption+)  
paulson@13223
   563
apply (simp add: ball_conj_distrib omult_Limit image_function)
paulson@13223
   564
done
paulson@13223
   565
paulson@13268
   566
lemma (in M_ord_arith) is_omult_fun_eq_omult:
paulson@13223
   567
    "[| is_omult_fun(M,i,J,f); M(J); M(f); Ord(i); Ord(j) |] 
paulson@13223
   568
     ==> j<J --> f`j = i**j"
paulson@13223
   569
apply (erule_tac i=j in trans_induct3)
paulson@13223
   570
apply (safe del: impCE)
paulson@13223
   571
  apply (simp add: is_omult_fun_apply_0) 
paulson@13223
   572
 apply (subgoal_tac "x<J") 
paulson@13223
   573
  apply (simp add: is_omult_fun_apply_succ omult_succ)  
paulson@13223
   574
 apply (blast intro: lt_trans) 
paulson@13223
   575
apply (subgoal_tac "\<forall>k\<in>x. k<J")
paulson@13223
   576
 apply (simp add: is_omult_fun_apply_Limit omult_Limit) 
paulson@13223
   577
apply (blast intro: lt_trans ltI lt_Ord) 
paulson@13223
   578
done
paulson@13223
   579
paulson@13268
   580
lemma (in M_ord_arith) omult_abs:
paulson@13223
   581
    "[| M(i); M(j); M(k); Ord(i); Ord(j) |] ==> is_omult(M,i,j,k) <-> k = i**j"
paulson@13352
   582
apply (simp add: is_omult_def is_omult_fun_eq_omult)
paulson@13223
   583
apply (frule exists_omult_fun [of j i], blast+)
paulson@13223
   584
done
paulson@13223
   585
paulson@13223
   586
end
paulson@13223
   587