| author | wenzelm | 
| Thu, 30 Oct 1997 17:00:34 +0100 | |
| changeset 4047 | 67b5552b1067 | 
| parent 3919 | c036caebfc75 | 
| child 4059 | 59c1422c9da5 | 
| permissions | -rw-r--r-- | 
| 1475 | 1  | 
(* Title: HOL/wf.ML  | 
| 923 | 2  | 
ID: $Id$  | 
| 1475 | 3  | 
Author: Tobias Nipkow, with minor changes by Konrad Slind  | 
4  | 
Copyright 1992 University of Cambridge/1995 TU Munich  | 
|
| 923 | 5  | 
|
| 3198 | 6  | 
Wellfoundedness, induction, and recursion  | 
| 923 | 7  | 
*)  | 
8  | 
||
9  | 
open WF;  | 
|
10  | 
||
| 950 | 11  | 
val H_cong = read_instantiate [("f","H")] (standard(refl RS cong RS cong));
 | 
| 923 | 12  | 
val H_cong1 = refl RS H_cong;  | 
13  | 
||
14  | 
(*Restriction to domain A. If r is well-founded over A then wf(r)*)  | 
|
15  | 
val [prem1,prem2] = goalw WF.thy [wf_def]  | 
|
| 1642 | 16  | 
"[| r <= A Times A; \  | 
| 
972
 
e61b058d58d2
changed syntax of tuples from <..., ...> to (..., ...)
 
clasohm 
parents: 
950 
diff
changeset
 | 
17  | 
\ !!x P. [| ! x. (! y. (y,x) : r --> P(y)) --> P(x); x:A |] ==> P(x) |] \  | 
| 923 | 18  | 
\ ==> wf(r)";  | 
| 3708 | 19  | 
by (Clarify_tac 1);  | 
| 923 | 20  | 
by (rtac allE 1);  | 
21  | 
by (assume_tac 1);  | 
|
| 
1786
 
8a31d85d27b8
best_tac, deepen_tac and safe_tac now also use default claset.
 
berghofe 
parents: 
1771 
diff
changeset
 | 
22  | 
by (best_tac (!claset addSEs [prem1 RS subsetD RS SigmaE2] addIs [prem2]) 1);  | 
| 923 | 23  | 
qed "wfI";  | 
24  | 
||
25  | 
val major::prems = goalw WF.thy [wf_def]  | 
|
26  | 
"[| wf(r); \  | 
|
| 
972
 
e61b058d58d2
changed syntax of tuples from <..., ...> to (..., ...)
 
clasohm 
parents: 
950 
diff
changeset
 | 
27  | 
\ !!x.[| ! y. (y,x): r --> P(y) |] ==> P(x) \  | 
| 923 | 28  | 
\ |] ==> P(a)";  | 
29  | 
by (rtac (major RS spec RS mp RS spec) 1);  | 
|
| 2935 | 30  | 
by (blast_tac (!claset addIs prems) 1);  | 
| 923 | 31  | 
qed "wf_induct";  | 
32  | 
||
33  | 
(*Perform induction on i, then prove the wf(r) subgoal using prems. *)  | 
|
34  | 
fun wf_ind_tac a prems i =  | 
|
35  | 
    EVERY [res_inst_tac [("a",a)] wf_induct i,
 | 
|
| 1465 | 36  | 
rename_last_tac a ["1"] (i+1),  | 
37  | 
ares_tac prems i];  | 
|
| 923 | 38  | 
|
| 
972
 
e61b058d58d2
changed syntax of tuples from <..., ...> to (..., ...)
 
clasohm 
parents: 
950 
diff
changeset
 | 
39  | 
val prems = goal WF.thy "[| wf(r); (a,x):r; (x,a):r |] ==> P";  | 
| 
 
e61b058d58d2
changed syntax of tuples from <..., ...> to (..., ...)
 
clasohm 
parents: 
950 
diff
changeset
 | 
40  | 
by (subgoal_tac "! x. (a,x):r --> (x,a):r --> P" 1);  | 
| 2935 | 41  | 
by (blast_tac (!claset addIs prems) 1);  | 
| 923 | 42  | 
by (wf_ind_tac "a" prems 1);  | 
| 2935 | 43  | 
by (Blast_tac 1);  | 
| 923 | 44  | 
qed "wf_asym";  | 
45  | 
||
| 
972
 
e61b058d58d2
changed syntax of tuples from <..., ...> to (..., ...)
 
clasohm 
parents: 
950 
diff
changeset
 | 
46  | 
val prems = goal WF.thy "[| wf(r); (a,a): r |] ==> P";  | 
| 923 | 47  | 
by (rtac wf_asym 1);  | 
48  | 
by (REPEAT (resolve_tac prems 1));  | 
|
| 1618 | 49  | 
qed "wf_irrefl";  | 
| 923 | 50  | 
|
| 1475 | 51  | 
(*transitive closure of a wf relation is wf! *)  | 
| 923 | 52  | 
val [prem] = goal WF.thy "wf(r) ==> wf(r^+)";  | 
53  | 
by (rewtac wf_def);  | 
|
| 3708 | 54  | 
by (Clarify_tac 1);  | 
| 923 | 55  | 
(*must retain the universal formula for later use!*)  | 
56  | 
by (rtac allE 1 THEN assume_tac 1);  | 
|
57  | 
by (etac mp 1);  | 
|
58  | 
by (res_inst_tac [("a","x")] (prem RS wf_induct) 1);
 | 
|
59  | 
by (rtac (impI RS allI) 1);  | 
|
60  | 
by (etac tranclE 1);  | 
|
| 2935 | 61  | 
by (Blast_tac 1);  | 
62  | 
by (Blast_tac 1);  | 
|
| 923 | 63  | 
qed "wf_trancl";  | 
64  | 
||
65  | 
||
| 3198 | 66  | 
(*----------------------------------------------------------------------------  | 
67  | 
* Minimal-element characterization of well-foundedness  | 
|
68  | 
*---------------------------------------------------------------------------*)  | 
|
69  | 
||
70  | 
val wfr::_ = goalw WF.thy [wf_def]  | 
|
71  | 
"wf r ==> x:Q --> (? z:Q. ! y. (y,z):r --> y~:Q)";  | 
|
72  | 
by (rtac (wfr RS spec RS mp RS spec) 1);  | 
|
73  | 
by (Blast_tac 1);  | 
|
74  | 
val lemma1 = result();  | 
|
75  | 
||
76  | 
goalw WF.thy [wf_def]  | 
|
77  | 
"!!r. (! Q x. x:Q --> (? z:Q. ! y. (y,z):r --> y~:Q)) ==> wf r";  | 
|
| 3708 | 78  | 
by (Clarify_tac 1);  | 
| 3198 | 79  | 
by (dres_inst_tac [("x", "{x. ~ P x}")] spec 1);
 | 
80  | 
by (Blast_tac 1);  | 
|
81  | 
val lemma2 = result();  | 
|
82  | 
||
83  | 
goal WF.thy "wf r = (! Q x. x:Q --> (? z:Q. ! y. (y,z):r --> y~:Q))";  | 
|
84  | 
by (blast_tac (!claset addSIs [lemma1, lemma2]) 1);  | 
|
85  | 
qed "wf_eq_minimal";  | 
|
86  | 
||
| 
3413
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
87  | 
(*---------------------------------------------------------------------------  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
88  | 
* Wellfoundedness of subsets  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
89  | 
*---------------------------------------------------------------------------*)  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
90  | 
|
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
91  | 
goal thy "!!r. [| wf(r); p<=r |] ==> wf(p)";  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
92  | 
by (full_simp_tac (!simpset addsimps [wf_eq_minimal]) 1);  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
93  | 
by (Fast_tac 1);  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
94  | 
qed "wf_subset";  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
95  | 
|
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
96  | 
(*---------------------------------------------------------------------------  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
97  | 
* Wellfoundedness of the empty relation.  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
98  | 
*---------------------------------------------------------------------------*)  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
99  | 
|
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
100  | 
goal thy "wf({})";
 | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
101  | 
by (simp_tac (!simpset addsimps [wf_def]) 1);  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
102  | 
qed "wf_empty";  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
103  | 
AddSIs [wf_empty];  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
104  | 
|
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
105  | 
(*---------------------------------------------------------------------------  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
106  | 
* Wellfoundedness of `insert'  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
107  | 
*---------------------------------------------------------------------------*)  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
108  | 
|
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
109  | 
goal WF.thy "wf(insert (y,x) r) = (wf(r) & (x,y) ~: r^*)";  | 
| 3457 | 110  | 
by (rtac iffI 1);  | 
111  | 
by (blast_tac (!claset addEs [wf_trancl RS wf_irrefl] addIs  | 
|
| 
3413
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
112  | 
[rtrancl_into_trancl1,wf_subset,impOfSubs rtrancl_mono]) 1);  | 
| 3457 | 113  | 
by (asm_full_simp_tac (!simpset addsimps [wf_eq_minimal]) 1);  | 
114  | 
by (safe_tac (!claset));  | 
|
115  | 
by (EVERY1[rtac allE, atac, etac impE, Blast_tac]);  | 
|
116  | 
by (etac bexE 1);  | 
|
117  | 
by (rename_tac "a" 1);  | 
|
118  | 
by (case_tac "a = x" 1);  | 
|
119  | 
 by (res_inst_tac [("x","a")]bexI 2);
 | 
|
120  | 
by (assume_tac 3);  | 
|
121  | 
by (Blast_tac 2);  | 
|
122  | 
by (case_tac "y:Q" 1);  | 
|
123  | 
by (Blast_tac 2);  | 
|
124  | 
by (res_inst_tac [("x","{z. z:Q & (z,y) : r^*}")]allE 1);
 | 
|
125  | 
by (assume_tac 1);  | 
|
126  | 
by (fast_tac (!claset addIs [rtrancl_into_rtrancl2]) 1);  | 
|
| 
3413
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
127  | 
qed "wf_insert";  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
128  | 
AddIffs [wf_insert];  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
129  | 
|
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
130  | 
(*** acyclic ***)  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
131  | 
|
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
132  | 
goalw WF.thy [acyclic_def]  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
133  | 
"!!r. wf r ==> acyclic r";  | 
| 3457 | 134  | 
by (blast_tac (!claset addEs [wf_trancl RS wf_irrefl]) 1);  | 
| 
3413
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
135  | 
qed "wf_acyclic";  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
136  | 
|
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
137  | 
goalw WF.thy [acyclic_def]  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
138  | 
"acyclic(insert (y,x) r) = (acyclic r & (x,y) ~: r^*)";  | 
| 3457 | 139  | 
by (simp_tac (!simpset addsimps [trancl_insert]) 1);  | 
140  | 
by (blast_tac (!claset addEs [make_elim rtrancl_trans]) 1);  | 
|
| 
3413
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
141  | 
qed "acyclic_insert";  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
142  | 
AddIffs [acyclic_insert];  | 
| 
 
c1f63cc3a768
Finite.ML Finite.thy: Replaced `finite subset of' by mere `finite'.
 
nipkow 
parents: 
3320 
diff
changeset
 | 
143  | 
|
| 3439 | 144  | 
goalw WF.thy [acyclic_def] "acyclic(r^-1) = acyclic r";  | 
| 3457 | 145  | 
by (simp_tac (!simpset addsimps [trancl_inverse]) 1);  | 
| 3439 | 146  | 
qed "acyclic_inverse";  | 
| 3198 | 147  | 
|
| 923 | 148  | 
(** cut **)  | 
149  | 
||
150  | 
(*This rewrite rule works upon formulae; thus it requires explicit use of  | 
|
151  | 
H_cong to expose the equality*)  | 
|
152  | 
goalw WF.thy [cut_def]  | 
|
| 
972
 
e61b058d58d2
changed syntax of tuples from <..., ...> to (..., ...)
 
clasohm 
parents: 
950 
diff
changeset
 | 
153  | 
"(cut f r x = cut g r x) = (!y. (y,x):r --> f(y)=g(y))";  | 
| 3919 | 154  | 
by (simp_tac (HOL_ss addsimps [expand_fun_eq] addsplits [expand_if]) 1);  | 
| 1475 | 155  | 
qed "cuts_eq";  | 
| 923 | 156  | 
|
| 
972
 
e61b058d58d2
changed syntax of tuples from <..., ...> to (..., ...)
 
clasohm 
parents: 
950 
diff
changeset
 | 
157  | 
goalw WF.thy [cut_def] "!!x. (x,a):r ==> (cut f r a)(x) = f(x)";  | 
| 1552 | 158  | 
by (asm_simp_tac HOL_ss 1);  | 
| 923 | 159  | 
qed "cut_apply";  | 
160  | 
||
161  | 
(*** is_recfun ***)  | 
|
162  | 
||
163  | 
goalw WF.thy [is_recfun_def,cut_def]  | 
|
| 3320 | 164  | 
"!!f. [| is_recfun r H a f; ~(b,a):r |] ==> f(b) = arbitrary";  | 
| 923 | 165  | 
by (etac ssubst 1);  | 
| 1552 | 166  | 
by (asm_simp_tac HOL_ss 1);  | 
| 923 | 167  | 
qed "is_recfun_undef";  | 
168  | 
||
169  | 
(*** NOTE! some simplifications need a different finish_tac!! ***)  | 
|
170  | 
fun indhyp_tac hyps =  | 
|
171  | 
(cut_facts_tac hyps THEN'  | 
|
172  | 
DEPTH_SOLVE_1 o (ares_tac [TrueI] ORELSE'  | 
|
| 1465 | 173  | 
eresolve_tac [transD, mp, allE]));  | 
| 
2637
 
e9b203f854ae
reflecting my recent changes of the simplifier and classical reasoner
 
oheimb 
parents: 
2031 
diff
changeset
 | 
174  | 
val wf_super_ss = HOL_ss addSolver indhyp_tac;  | 
| 923 | 175  | 
|
176  | 
val prems = goalw WF.thy [is_recfun_def,cut_def]  | 
|
| 1475 | 177  | 
"[| wf(r); trans(r); is_recfun r H a f; is_recfun r H b g |] ==> \  | 
| 
972
 
e61b058d58d2
changed syntax of tuples from <..., ...> to (..., ...)
 
clasohm 
parents: 
950 
diff
changeset
 | 
178  | 
\ (x,a):r --> (x,b):r --> f(x)=g(x)";  | 
| 923 | 179  | 
by (cut_facts_tac prems 1);  | 
180  | 
by (etac wf_induct 1);  | 
|
181  | 
by (REPEAT (rtac impI 1 ORELSE etac ssubst 1));  | 
|
182  | 
by (asm_simp_tac (wf_super_ss addcongs [if_cong]) 1);  | 
|
| 
1485
 
240cc98b94a7
Added qed_spec_mp to avoid renaming of bound vars in 'th RS spec'
 
nipkow 
parents: 
1475 
diff
changeset
 | 
183  | 
qed_spec_mp "is_recfun_equal";  | 
| 923 | 184  | 
|
185  | 
||
186  | 
val prems as [wfr,transr,recfa,recgb,_] = goalw WF.thy [cut_def]  | 
|
187  | 
"[| wf(r); trans(r); \  | 
|
| 1475 | 188  | 
\ is_recfun r H a f; is_recfun r H b g; (b,a):r |] ==> \  | 
| 923 | 189  | 
\ cut f r b = g";  | 
190  | 
val gundef = recgb RS is_recfun_undef  | 
|
191  | 
and fisg = recgb RS (recfa RS (transr RS (wfr RS is_recfun_equal)));  | 
|
192  | 
by (cut_facts_tac prems 1);  | 
|
193  | 
by (rtac ext 1);  | 
|
194  | 
by (asm_simp_tac (wf_super_ss addsimps [gundef,fisg]  | 
|
| 3919 | 195  | 
addsplits [expand_if]) 1);  | 
| 923 | 196  | 
qed "is_recfun_cut";  | 
197  | 
||
198  | 
(*** Main Existence Lemma -- Basic Properties of the_recfun ***)  | 
|
199  | 
||
200  | 
val prems = goalw WF.thy [the_recfun_def]  | 
|
| 1475 | 201  | 
"is_recfun r H a f ==> is_recfun r H a (the_recfun r H a)";  | 
202  | 
by (res_inst_tac [("P", "is_recfun r H a")] selectI 1);
 | 
|
| 923 | 203  | 
by (resolve_tac prems 1);  | 
204  | 
qed "is_the_recfun";  | 
|
205  | 
||
206  | 
val prems = goal WF.thy  | 
|
| 1475 | 207  | 
"[| wf(r); trans(r) |] ==> is_recfun r H a (the_recfun r H a)";  | 
208  | 
by (cut_facts_tac prems 1);  | 
|
209  | 
by (wf_ind_tac "a" prems 1);  | 
|
210  | 
  by (res_inst_tac [("f","cut (%y. H (the_recfun r H y) y) r a1")]
 | 
|
211  | 
is_the_recfun 1);  | 
|
| 1552 | 212  | 
by (rewtac is_recfun_def);  | 
| 2031 | 213  | 
by (stac cuts_eq 1);  | 
| 1475 | 214  | 
by (rtac allI 1);  | 
215  | 
by (rtac impI 1);  | 
|
216  | 
  by (res_inst_tac [("f1","H"),("x","y")](arg_cong RS fun_cong) 1);
 | 
|
217  | 
by (subgoal_tac  | 
|
218  | 
"the_recfun r H y = cut(%x. H(cut(the_recfun r H y) r x) x) r y" 1);  | 
|
219  | 
by (etac allE 2);  | 
|
220  | 
by (dtac impE 2);  | 
|
221  | 
by (atac 2);  | 
|
222  | 
by (atac 3);  | 
|
223  | 
by (atac 2);  | 
|
224  | 
by (etac ssubst 1);  | 
|
225  | 
by (simp_tac (HOL_ss addsimps [cuts_eq]) 1);  | 
|
226  | 
by (rtac allI 1);  | 
|
227  | 
by (rtac impI 1);  | 
|
228  | 
by (asm_simp_tac (wf_super_ss addsimps[cut_apply,is_recfun_cut,cuts_eq]) 1);  | 
|
229  | 
  by (res_inst_tac [("f1","H"),("x","ya")](arg_cong RS fun_cong) 1);
 | 
|
230  | 
by (fold_tac [is_recfun_def]);  | 
|
231  | 
by (asm_simp_tac (wf_super_ss addsimps[cut_apply,is_recfun_cut,cuts_eq]) 1);  | 
|
| 923 | 232  | 
qed "unfold_the_recfun";  | 
233  | 
||
| 1475 | 234  | 
val unwind1_the_recfun = rewrite_rule[is_recfun_def] unfold_the_recfun;  | 
| 923 | 235  | 
|
| 1475 | 236  | 
(*--------------Old proof-----------------------------------------------------  | 
| 923 | 237  | 
val prems = goal WF.thy  | 
| 1475 | 238  | 
"[| wf(r); trans(r) |] ==> is_recfun r H a (the_recfun r H a)";  | 
239  | 
by (cut_facts_tac prems 1);  | 
|
240  | 
by (wf_ind_tac "a" prems 1);  | 
|
241  | 
by (res_inst_tac [("f", "cut (%y. wftrec r H y) r a1")] is_the_recfun 1); 
 | 
|
242  | 
by (rewrite_goals_tac [is_recfun_def, wftrec_def]);  | 
|
| 2031 | 243  | 
by (stac cuts_eq 1);  | 
| 1475 | 244  | 
(*Applying the substitution: must keep the quantified assumption!!*)  | 
| 3708 | 245  | 
by (EVERY1 [Clarify_tac, rtac H_cong1, rtac allE, atac,  | 
| 1475 | 246  | 
etac (mp RS ssubst), atac]);  | 
247  | 
by (fold_tac [is_recfun_def]);  | 
|
248  | 
by (asm_simp_tac (wf_super_ss addsimps[cut_apply,is_recfun_cut,cuts_eq]) 1);  | 
|
249  | 
qed "unfold_the_recfun";  | 
|
250  | 
---------------------------------------------------------------------------*)  | 
|
| 923 | 251  | 
|
252  | 
(** Removal of the premise trans(r) **)  | 
|
| 1475 | 253  | 
val th = rewrite_rule[is_recfun_def]  | 
254  | 
(trans_trancl RSN (2,(wf_trancl RS unfold_the_recfun)));  | 
|
| 923 | 255  | 
|
256  | 
goalw WF.thy [wfrec_def]  | 
|
| 1475 | 257  | 
"!!r. wf(r) ==> wfrec r H a = H (cut (wfrec r H) r a) a";  | 
258  | 
by (rtac H_cong 1);  | 
|
259  | 
by (rtac refl 2);  | 
|
260  | 
by (simp_tac (HOL_ss addsimps [cuts_eq]) 1);  | 
|
261  | 
by (rtac allI 1);  | 
|
262  | 
by (rtac impI 1);  | 
|
263  | 
by (simp_tac(HOL_ss addsimps [wfrec_def]) 1);  | 
|
264  | 
by (res_inst_tac [("a1","a")] (th RS ssubst) 1);
 | 
|
265  | 
by (atac 1);  | 
|
266  | 
by (forward_tac[wf_trancl] 1);  | 
|
267  | 
by (forward_tac[r_into_trancl] 1);  | 
|
268  | 
by (asm_simp_tac (HOL_ss addsimps [cut_apply]) 1);  | 
|
269  | 
by (rtac H_cong 1); (*expose the equality of cuts*)  | 
|
270  | 
by (rtac refl 2);  | 
|
271  | 
by (simp_tac (HOL_ss addsimps [cuts_eq, cut_apply, r_into_trancl]) 1);  | 
|
| 3708 | 272  | 
by (Clarify_tac 1);  | 
| 
1485
 
240cc98b94a7
Added qed_spec_mp to avoid renaming of bound vars in 'th RS spec'
 
nipkow 
parents: 
1475 
diff
changeset
 | 
273  | 
by (res_inst_tac [("r","r^+")] is_recfun_equal 1);
 | 
| 1475 | 274  | 
by (atac 1);  | 
275  | 
by (rtac trans_trancl 1);  | 
|
276  | 
by (rtac unfold_the_recfun 1);  | 
|
277  | 
by (atac 1);  | 
|
278  | 
by (rtac trans_trancl 1);  | 
|
279  | 
by (rtac unfold_the_recfun 1);  | 
|
280  | 
by (atac 1);  | 
|
281  | 
by (rtac trans_trancl 1);  | 
|
282  | 
by (rtac transD 1);  | 
|
283  | 
by (rtac trans_trancl 1);  | 
|
284  | 
by (forw_inst_tac [("a","ya")] r_into_trancl 1);
 | 
|
285  | 
by (atac 1);  | 
|
286  | 
by (atac 1);  | 
|
287  | 
by (forw_inst_tac [("a","ya")] r_into_trancl 1);
 | 
|
288  | 
by (atac 1);  | 
|
289  | 
qed "wfrec";  | 
|
290  | 
||
291  | 
(*--------------Old proof-----------------------------------------------------  | 
|
292  | 
goalw WF.thy [wfrec_def]  | 
|
293  | 
"!!r. wf(r) ==> wfrec r H a = H (cut (wfrec r H) r a) a";  | 
|
| 923 | 294  | 
by (etac (wf_trancl RS wftrec RS ssubst) 1);  | 
295  | 
by (rtac trans_trancl 1);  | 
|
296  | 
by (rtac (refl RS H_cong) 1); (*expose the equality of cuts*)  | 
|
| 1475 | 297  | 
by (simp_tac (HOL_ss addsimps [cuts_eq, cut_apply, r_into_trancl]) 1);  | 
| 923 | 298  | 
qed "wfrec";  | 
| 1475 | 299  | 
---------------------------------------------------------------------------*)  | 
| 923 | 300  | 
|
| 1475 | 301  | 
(*---------------------------------------------------------------------------  | 
302  | 
* This form avoids giant explosions in proofs. NOTE USE OF ==  | 
|
303  | 
*---------------------------------------------------------------------------*)  | 
|
| 923 | 304  | 
val rew::prems = goal WF.thy  | 
| 1475 | 305  | 
"[| f==wfrec r H; wf(r) |] ==> f(a) = H (cut f r a) a";  | 
| 923 | 306  | 
by (rewtac rew);  | 
307  | 
by (REPEAT (resolve_tac (prems@[wfrec]) 1));  | 
|
308  | 
qed "def_wfrec";  | 
|
| 1475 | 309  | 
|
| 3198 | 310  | 
|
311  | 
(**** TFL variants ****)  | 
|
312  | 
||
313  | 
goal WF.thy  | 
|
314  | 
"!R. wf R --> (!P. (!x. (!y. (y,x):R --> P y) --> P x) --> (!x. P x))";  | 
|
| 3708 | 315  | 
by (Clarify_tac 1);  | 
| 3198 | 316  | 
by (res_inst_tac [("r","R"),("P","P"), ("a","x")] wf_induct 1);
 | 
317  | 
by (assume_tac 1);  | 
|
318  | 
by (Blast_tac 1);  | 
|
319  | 
qed"tfl_wf_induct";  | 
|
320  | 
||
321  | 
goal WF.thy "!f R. (x,a):R --> (cut f R a)(x) = f(x)";  | 
|
| 3708 | 322  | 
by (Clarify_tac 1);  | 
| 3198 | 323  | 
by (rtac cut_apply 1);  | 
324  | 
by (assume_tac 1);  | 
|
325  | 
qed"tfl_cut_apply";  | 
|
326  | 
||
327  | 
goal WF.thy "!M R f. (f=wfrec R M) --> wf R --> (!x. f x = M (cut f R x) x)";  | 
|
| 3708 | 328  | 
by (Clarify_tac 1);  | 
329  | 
be wfrec 1;  | 
|
| 3198 | 330  | 
qed "tfl_wfrec";  |