| author | wenzelm | 
| Sat, 30 Nov 2024 17:14:30 +0100 | |
| changeset 81515 | 44c0028486db | 
| parent 81506 | f76a5849b570 | 
| child 81516 | 31b05aef022d | 
| permissions | -rw-r--r-- | 
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
1  | 
(* Title: Pure/term.ML  | 
| 
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
2  | 
Author: Lawrence C Paulson, Cambridge University Computer Laboratory  | 
| 29280 | 3  | 
Author: Makarius  | 
| 
1364
 
8ea1a962ad72
files now define a structure to allow SML/NJ to optimize the code
 
clasohm 
parents: 
1029 
diff
changeset
 | 
4  | 
|
| 4444 | 5  | 
Simply typed lambda-calculus: types, terms, and basic operations.  | 
| 0 | 6  | 
*)  | 
7  | 
||
| 
29257
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
8  | 
infix 9 $;  | 
| 
1364
 
8ea1a962ad72
files now define a structure to allow SML/NJ to optimize the code
 
clasohm 
parents: 
1029 
diff
changeset
 | 
9  | 
infixr 5 -->;  | 
| 4444 | 10  | 
infixr --->;  | 
11  | 
infix aconv;  | 
|
| 
1364
 
8ea1a962ad72
files now define a structure to allow SML/NJ to optimize the code
 
clasohm 
parents: 
1029 
diff
changeset
 | 
12  | 
|
| 4444 | 13  | 
signature BASIC_TERM =  | 
14  | 
sig  | 
|
| 34922 | 15  | 
type indexname = string * int  | 
16  | 
type class = string  | 
|
17  | 
type sort = class list  | 
|
18  | 
type arity = string * sort list * sort  | 
|
| 4444 | 19  | 
datatype typ =  | 
20  | 
Type of string * typ list |  | 
|
21  | 
TFree of string * sort |  | 
|
22  | 
TVar of indexname * sort  | 
|
| 16537 | 23  | 
datatype term =  | 
24  | 
Const of string * typ |  | 
|
25  | 
Free of string * typ |  | 
|
26  | 
Var of indexname * typ |  | 
|
27  | 
Bound of int |  | 
|
28  | 
Abs of string * typ * term |  | 
|
| 17756 | 29  | 
$ of term * term  | 
| 16537 | 30  | 
exception TYPE of string * typ list * term list  | 
31  | 
exception TERM of string * term list  | 
|
| 21353 | 32  | 
val dummyS: sort  | 
| 16710 | 33  | 
val dummyT: typ  | 
34  | 
val no_dummyT: typ -> typ  | 
|
| 4444 | 35  | 
val --> : typ * typ -> typ  | 
36  | 
val ---> : typ list * typ -> typ  | 
|
| 67703 | 37  | 
val is_Type: typ -> bool  | 
38  | 
val is_TFree: typ -> bool  | 
|
39  | 
val is_TVar: typ -> bool  | 
|
| 80675 | 40  | 
val eq_Type_name: typ * typ -> bool  | 
| 16710 | 41  | 
val dest_Type: typ -> string * typ list  | 
| 80632 | 42  | 
val dest_Type_name: typ -> string  | 
43  | 
val dest_Type_args: typ -> typ list  | 
|
| 67703 | 44  | 
val dest_TFree: typ -> string * sort  | 
| 16710 | 45  | 
val dest_TVar: typ -> indexname * sort  | 
46  | 
val is_Bound: term -> bool  | 
|
47  | 
val is_Const: term -> bool  | 
|
48  | 
val is_Free: term -> bool  | 
|
49  | 
val is_Var: term -> bool  | 
|
| 80675 | 50  | 
val eq_Const_name: term * term -> bool  | 
| 16710 | 51  | 
val dest_Const: term -> string * typ  | 
| 80635 | 52  | 
val dest_Const_name: term -> string  | 
53  | 
val dest_Const_type: term -> typ  | 
|
| 16710 | 54  | 
val dest_Free: term -> string * typ  | 
55  | 
val dest_Var: term -> indexname * typ  | 
|
| 35227 | 56  | 
val dest_comb: term -> term * term  | 
| 4444 | 57  | 
val domain_type: typ -> typ  | 
| 4480 | 58  | 
val range_type: typ -> typ  | 
| 40840 | 59  | 
val dest_funT: typ -> typ * typ  | 
| 4444 | 60  | 
val binder_types: typ -> typ list  | 
61  | 
val body_type: typ -> typ  | 
|
62  | 
val strip_type: typ -> typ list * typ  | 
|
| 16710 | 63  | 
val type_of1: typ list * term -> typ  | 
| 4444 | 64  | 
val type_of: term -> typ  | 
| 16710 | 65  | 
val fastype_of1: typ list * term -> typ  | 
| 4444 | 66  | 
val fastype_of: term -> typ  | 
| 18927 | 67  | 
val strip_abs: term -> (string * typ) list * term  | 
| 4444 | 68  | 
val strip_abs_body: term -> term  | 
69  | 
val strip_abs_vars: term -> (string * typ) list  | 
|
70  | 
val strip_qnt_body: string -> term -> term  | 
|
71  | 
val strip_qnt_vars: string -> term -> (string * typ) list  | 
|
72  | 
val list_comb: term * term list -> term  | 
|
73  | 
val strip_comb: term -> term * term list  | 
|
74  | 
val head_of: term -> term  | 
|
75  | 
val size_of_term: term -> int  | 
|
| 
29882
 
29154e67731d
New command find_consts searching for constants by type (by Timothy Bourke).
 
kleing 
parents: 
29286 
diff
changeset
 | 
76  | 
val size_of_typ: typ -> int  | 
| 79409 | 77  | 
val map_atyps: typ Same.operation -> typ -> typ  | 
78  | 
val map_aterms: term Same.operation -> term -> term  | 
|
79  | 
val map_types: typ Same.operation -> term -> term  | 
|
80  | 
val map_type_tvar: (indexname * sort, typ) Same.function -> typ -> typ  | 
|
81  | 
val map_type_tfree: (string * sort, typ) Same.function -> typ -> typ  | 
|
| 16943 | 82  | 
val fold_atyps: (typ -> 'a -> 'a) -> typ -> 'a -> 'a  | 
| 35986 | 83  | 
val fold_atyps_sorts: (typ * sort -> 'a -> 'a) -> typ -> 'a -> 'a  | 
| 16943 | 84  | 
val fold_aterms: (term -> 'a -> 'a) -> term -> 'a -> 'a  | 
85  | 
val fold_term_types: (term -> typ -> 'a -> 'a) -> term -> 'a -> 'a  | 
|
86  | 
val fold_types: (typ -> 'a -> 'a) -> term -> 'a -> 'a  | 
|
| 24483 | 87  | 
val burrow_types: (typ list -> typ list) -> term list -> term list  | 
| 16710 | 88  | 
val aconv: term * term -> bool  | 
| 4444 | 89  | 
val propT: typ  | 
90  | 
val strip_all_body: term -> term  | 
|
91  | 
val strip_all_vars: term -> (string * typ) list  | 
|
| 
79172
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
92  | 
val incr_bv_same: int -> int -> term Same.operation  | 
| 
79170
 
4affbdbeefd4
clarified signature: more standard argument order;
 
wenzelm 
parents: 
79168 
diff
changeset
 | 
93  | 
val incr_bv: int -> int -> term -> term  | 
| 4444 | 94  | 
val incr_boundvars: int -> term -> term  | 
95  | 
val add_loose_bnos: term * int * int list -> int list  | 
|
96  | 
val loose_bnos: term -> int list  | 
|
97  | 
val loose_bvar: term * int -> bool  | 
|
98  | 
val loose_bvar1: term * int -> bool  | 
|
| 79202 | 99  | 
val subst_bounds_same: term list -> int -> term Same.operation  | 
| 4444 | 100  | 
val subst_bounds: term list * term -> term  | 
101  | 
val subst_bound: term * term -> term  | 
|
102  | 
val betapply: term * term -> term  | 
|
| 18183 | 103  | 
val betapplys: term * term list -> term  | 
| 4444 | 104  | 
val subst_free: (term * term) list -> term -> term  | 
105  | 
val abstract_over: term * term -> term  | 
|
| 11922 | 106  | 
val lambda: term -> term -> term  | 
| 44241 | 107  | 
val absfree: string * typ -> term -> term  | 
108  | 
val absdummy: typ -> term -> term  | 
|
| 16710 | 109  | 
val subst_atomic: (term * term) list -> term -> term  | 
110  | 
val typ_subst_atomic: (typ * typ) list -> typ -> typ  | 
|
111  | 
val subst_atomic_types: (typ * typ) list -> term -> term  | 
|
112  | 
val typ_subst_TVars: (indexname * typ) list -> typ -> typ  | 
|
113  | 
val subst_TVars: (indexname * typ) list -> term -> term  | 
|
114  | 
val subst_Vars: (indexname * term) list -> term -> term  | 
|
115  | 
val subst_vars: (indexname * typ) list * (indexname * term) list -> term -> term  | 
|
116  | 
val is_first_order: string list -> term -> bool  | 
|
| 4444 | 117  | 
val maxidx_of_typ: typ -> int  | 
118  | 
val maxidx_of_typs: typ list -> int  | 
|
119  | 
val maxidx_of_term: term -> int  | 
|
| 61248 | 120  | 
val fold_subtypes: (typ -> 'a -> 'a) -> typ -> 'a -> 'a  | 
| 19909 | 121  | 
val exists_subtype: (typ -> bool) -> typ -> bool  | 
| 20531 | 122  | 
val exists_type: (typ -> bool) -> term -> bool  | 
| 16943 | 123  | 
val exists_subterm: (term -> bool) -> term -> bool  | 
| 16710 | 124  | 
val exists_Const: (string * typ -> bool) -> term -> bool  | 
| 76047 | 125  | 
val is_schematic: term -> bool  | 
| 4444 | 126  | 
end;  | 
| 0 | 127  | 
|
| 4444 | 128  | 
signature TERM =  | 
129  | 
sig  | 
|
130  | 
include BASIC_TERM  | 
|
| 79409 | 131  | 
val map_atyps_same: typ Same.operation -> typ Same.operation  | 
132  | 
val map_aterms_same: term Same.operation -> term Same.operation  | 
|
133  | 
val map_types_same: typ Same.operation -> term Same.operation  | 
|
| 19394 | 134  | 
val aT: sort -> typ  | 
135  | 
val itselfT: typ -> typ  | 
|
136  | 
val a_itselfT: typ  | 
|
| 22908 | 137  | 
val argument_type_of: term -> int -> typ  | 
| 
46219
 
426ed18eba43
discontinued old-style Term.list_abs in favour of plain Term.abs;
 
wenzelm 
parents: 
46218 
diff
changeset
 | 
138  | 
val abs: string * typ -> term -> term  | 
| 
74577
 
d4829a7333e2
clarified instantiation: local beta reduction after substitution, as for Envir.expand_term_defs;
 
wenzelm 
parents: 
74525 
diff
changeset
 | 
139  | 
val args_of: term -> term list  | 
| 
29257
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
140  | 
val add_tvar_namesT: typ -> indexname list -> indexname list  | 
| 
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
141  | 
val add_tvar_names: term -> indexname list -> indexname list  | 
| 16943 | 142  | 
val add_tvarsT: typ -> (indexname * sort) list -> (indexname * sort) list  | 
143  | 
val add_tvars: term -> (indexname * sort) list -> (indexname * sort) list  | 
|
| 
29257
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
144  | 
val add_var_names: term -> indexname list -> indexname list  | 
| 16943 | 145  | 
val add_vars: term -> (indexname * typ) list -> (indexname * typ) list  | 
| 
29257
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
146  | 
val add_tfree_namesT: typ -> string list -> string list  | 
| 
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
147  | 
val add_tfree_names: term -> string list -> string list  | 
| 16943 | 148  | 
val add_tfreesT: typ -> (string * sort) list -> (string * sort) list  | 
149  | 
val add_tfrees: term -> (string * sort) list -> (string * sort) list  | 
|
| 
29257
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
150  | 
val add_free_names: term -> string list -> string list  | 
| 16943 | 151  | 
val add_frees: term -> (string * typ) list -> (string * typ) list  | 
| 29286 | 152  | 
val add_const_names: term -> string list -> string list  | 
153  | 
val add_consts: term -> (string * typ) list -> (string * typ) list  | 
|
| 81505 | 154  | 
val declare_tfree_namesT: typ -> Name.context -> Name.context  | 
155  | 
val declare_tfree_names: term -> Name.context -> Name.context  | 
|
| 81515 | 156  | 
val declare_tvar_namesT: (int -> bool) -> typ -> Name.context -> Name.context  | 
157  | 
val declare_tvar_names: (int -> bool) -> term -> Name.context -> Name.context  | 
|
| 81505 | 158  | 
val declare_free_names: term -> Name.context -> Name.context  | 
| 81515 | 159  | 
val declare_var_names: (int -> bool) -> term -> Name.context -> Name.context  | 
| 25050 | 160  | 
val hidden_polymorphism: term -> (indexname * sort) list  | 
| 29278 | 161  | 
val declare_term_names: term -> Name.context -> Name.context  | 
162  | 
val variant_frees: term -> (string * 'a) list -> (string * 'a) list  | 
|
| 79411 | 163  | 
val smash_sortsT_same: sort -> typ Same.operation  | 
| 79439 | 164  | 
val smash_sortsT: sort -> typ -> typ  | 
165  | 
val smash_sorts: sort -> term -> term  | 
|
| 79411 | 166  | 
val strip_sortsT_same: typ Same.operation  | 
167  | 
val strip_sortsT: typ -> typ  | 
|
168  | 
val strip_sorts: term -> term  | 
|
| 29278 | 169  | 
val rename_wrt_term: term -> (string * 'a) list -> (string * 'a) list  | 
| 
29269
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
170  | 
val eq_ix: indexname * indexname -> bool  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
171  | 
val eq_tvar: (indexname * sort) * (indexname * sort) -> bool  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
172  | 
val eq_var: (indexname * typ) * (indexname * typ) -> bool  | 
| 
33537
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
173  | 
val aconv_untyped: term * term -> bool  | 
| 
29269
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
174  | 
val could_unify: term * term -> bool  | 
| 20109 | 175  | 
val strip_abs_eta: int -> term -> (string * typ) list * term  | 
| 48263 | 176  | 
val match_bvars: (term * term) -> (string * string) list -> (string * string) list  | 
| 22031 | 177  | 
val map_abs_vars: (string -> string) -> term -> term  | 
| 12981 | 178  | 
val rename_abs: term -> term -> term -> term option  | 
| 
42083
 
e1209fc7ecdc
added Term.is_open and Term.is_dependent convenience, to cover common situations of loose bounds;
 
wenzelm 
parents: 
40844 
diff
changeset
 | 
179  | 
val is_open: term -> bool  | 
| 
 
e1209fc7ecdc
added Term.is_open and Term.is_dependent convenience, to cover common situations of loose bounds;
 
wenzelm 
parents: 
40844 
diff
changeset
 | 
180  | 
val is_dependent: term -> bool  | 
| 
61655
 
f217bbe4e93e
avoid vacuous quantification, as usual for shared variable scope;
 
wenzelm 
parents: 
61248 
diff
changeset
 | 
181  | 
val term_name: term -> string  | 
| 
60404
 
422b63ef0147
clarified abstracted term bindings (again, see c8384ff11711);
 
wenzelm 
parents: 
60311 
diff
changeset
 | 
182  | 
val dependent_lambda_name: string * term -> term -> term  | 
| 32198 | 183  | 
val lambda_name: string * term -> term -> term  | 
| 25050 | 184  | 
val close_schematic_term: term -> term  | 
| 16710 | 185  | 
val maxidx_typ: typ -> int -> int  | 
186  | 
val maxidx_typs: typ list -> int -> int  | 
|
187  | 
val maxidx_term: term -> int -> int  | 
|
| 63619 | 188  | 
val could_beta_contract: term -> bool  | 
189  | 
val could_eta_contract: term -> bool  | 
|
| 74446 | 190  | 
val used_free: string -> term -> bool  | 
| 
74525
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
191  | 
exception USED_FREE of string * term  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
192  | 
val dest_abs_fresh: string -> term -> (string * typ) * term  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
193  | 
val dest_abs_global: term -> (string * typ) * term  | 
| 18253 | 194  | 
val dummy_pattern: typ -> term  | 
| 45156 | 195  | 
val dummy: term  | 
196  | 
val dummy_prop: term  | 
|
| 22723 | 197  | 
val is_dummy_pattern: term -> bool  | 
| 24733 | 198  | 
val free_dummy_patterns: term -> Name.context -> term * Name.context  | 
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
199  | 
val no_dummy_patterns: term -> term  | 
| 24762 | 200  | 
val replace_dummy_patterns: term -> int -> term * int  | 
| 16035 | 201  | 
val show_dummy_patterns: term -> term  | 
| 
14786
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
202  | 
val string_of_vname: indexname -> string  | 
| 
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
203  | 
val string_of_vname': indexname -> string  | 
| 4444 | 204  | 
end;  | 
205  | 
||
206  | 
structure Term: TERM =  | 
|
| 
1364
 
8ea1a962ad72
files now define a structure to allow SML/NJ to optimize the code
 
clasohm 
parents: 
1029 
diff
changeset
 | 
207  | 
struct  | 
| 0 | 208  | 
|
209  | 
(*Indexnames can be quickly renamed by adding an offset to the integer part,  | 
|
210  | 
for resolution.*)  | 
|
| 16537 | 211  | 
type indexname = string * int;  | 
| 0 | 212  | 
|
| 63611 | 213  | 
(*Types are classified by sorts.*)  | 
| 0 | 214  | 
type class = string;  | 
215  | 
type sort = class list;  | 
|
| 
14829
 
cfa5fe01a7b7
moved read_int etc. to library.ML; added type 'arity';
 
wenzelm 
parents: 
14786 
diff
changeset
 | 
216  | 
type arity = string * sort list * sort;  | 
| 0 | 217  | 
|
| 63611 | 218  | 
(*The sorts attached to TFrees and TVars specify the sort of that variable.*)  | 
| 0 | 219  | 
datatype typ = Type of string * typ list  | 
220  | 
| TFree of string * sort  | 
|
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
221  | 
| TVar of indexname * sort;  | 
| 0 | 222  | 
|
| 
6033
 
c8c69a4a7762
moved dest_Type to term.ML from HOL/Tools/primrec_package
 
paulson 
parents: 
5986 
diff
changeset
 | 
223  | 
(*Terms. Bound variables are indicated by depth number.  | 
| 0 | 224  | 
Free variables, (scheme) variables and constants have names.  | 
| 4626 | 225  | 
An term is "closed" if every bound variable of level "lev"  | 
| 13000 | 226  | 
is enclosed by at least "lev" abstractions.  | 
| 0 | 227  | 
|
228  | 
It is possible to create meaningless terms containing loose bound vars  | 
|
229  | 
or type mismatches. But such terms are not allowed in rules. *)  | 
|
230  | 
||
| 13000 | 231  | 
datatype term =  | 
| 0 | 232  | 
Const of string * typ  | 
| 13000 | 233  | 
| Free of string * typ  | 
| 0 | 234  | 
| Var of indexname * typ  | 
235  | 
| Bound of int  | 
|
236  | 
| Abs of string*typ*term  | 
|
| 3965 | 237  | 
| op $ of term*term;  | 
| 0 | 238  | 
|
| 16537 | 239  | 
(*Errors involving type mismatches*)  | 
| 0 | 240  | 
exception TYPE of string * typ list * term list;  | 
241  | 
||
| 16537 | 242  | 
(*Errors errors involving terms*)  | 
| 0 | 243  | 
exception TERM of string * term list;  | 
244  | 
||
245  | 
(*Note variable naming conventions!  | 
|
246  | 
a,b,c: string  | 
|
247  | 
f,g,h: functions (including terms of function type)  | 
|
248  | 
i,j,m,n: int  | 
|
249  | 
t,u: term  | 
|
250  | 
v,w: indexnames  | 
|
251  | 
x,y: any  | 
|
252  | 
A,B,C: term (denoting formulae)  | 
|
253  | 
T,U: typ  | 
|
254  | 
*)  | 
|
255  | 
||
256  | 
||
| 
6033
 
c8c69a4a7762
moved dest_Type to term.ML from HOL/Tools/primrec_package
 
paulson 
parents: 
5986 
diff
changeset
 | 
257  | 
(** Types **)  | 
| 
 
c8c69a4a7762
moved dest_Type to term.ML from HOL/Tools/primrec_package
 
paulson 
parents: 
5986 
diff
changeset
 | 
258  | 
|
| 21353 | 259  | 
(*dummies for type-inference etc.*)  | 
260  | 
val dummyS = [""];  | 
|
| 16537 | 261  | 
val dummyT = Type ("dummy", []);
 | 
262  | 
||
263  | 
fun no_dummyT typ =  | 
|
264  | 
let  | 
|
265  | 
    fun check (T as Type ("dummy", _)) =
 | 
|
266  | 
          raise TYPE ("Illegal occurrence of '_' dummy type", [T], [])
 | 
|
267  | 
| check (Type (_, Ts)) = List.app check Ts  | 
|
268  | 
| check _ = ();  | 
|
269  | 
in check typ; typ end;  | 
|
270  | 
||
| 
6033
 
c8c69a4a7762
moved dest_Type to term.ML from HOL/Tools/primrec_package
 
paulson 
parents: 
5986 
diff
changeset
 | 
271  | 
fun S --> T = Type("fun",[S,T]);
 | 
| 
 
c8c69a4a7762
moved dest_Type to term.ML from HOL/Tools/primrec_package
 
paulson 
parents: 
5986 
diff
changeset
 | 
272  | 
|
| 
 
c8c69a4a7762
moved dest_Type to term.ML from HOL/Tools/primrec_package
 
paulson 
parents: 
5986 
diff
changeset
 | 
273  | 
(*handy for multiple args: [T1,...,Tn]--->T gives T1-->(T2--> ... -->T)*)  | 
| 15570 | 274  | 
val op ---> = Library.foldr (op -->);  | 
| 
6033
 
c8c69a4a7762
moved dest_Type to term.ML from HOL/Tools/primrec_package
 
paulson 
parents: 
5986 
diff
changeset
 | 
275  | 
|
| 67703 | 276  | 
|
277  | 
(** Discriminators **)  | 
|
278  | 
||
279  | 
fun is_Type (Type _) = true  | 
|
280  | 
| is_Type _ = false;  | 
|
281  | 
||
282  | 
fun is_TFree (TFree _) = true  | 
|
283  | 
| is_TFree _ = false;  | 
|
284  | 
||
285  | 
fun is_TVar (TVar _) = true  | 
|
286  | 
| is_TVar _ = false;  | 
|
287  | 
||
| 80675 | 288  | 
fun eq_Type_name (Type (a, _), Type (b, _)) = a = b  | 
289  | 
| eq_Type_name _ = false;  | 
|
290  | 
||
| 67703 | 291  | 
|
292  | 
(** Destructors **)  | 
|
293  | 
||
| 
6033
 
c8c69a4a7762
moved dest_Type to term.ML from HOL/Tools/primrec_package
 
paulson 
parents: 
5986 
diff
changeset
 | 
294  | 
fun dest_Type (Type x) = x  | 
| 
 
c8c69a4a7762
moved dest_Type to term.ML from HOL/Tools/primrec_package
 
paulson 
parents: 
5986 
diff
changeset
 | 
295  | 
  | dest_Type T = raise TYPE ("dest_Type", [T], []);
 | 
| 67703 | 296  | 
|
| 80632 | 297  | 
val dest_Type_name = #1 o dest_Type;  | 
298  | 
val dest_Type_args = #2 o dest_Type;  | 
|
299  | 
||
| 67703 | 300  | 
fun dest_TFree (TFree x) = x  | 
301  | 
  | dest_TFree T = raise TYPE ("dest_TFree", [T], []);
 | 
|
302  | 
||
| 15914 | 303  | 
fun dest_TVar (TVar x) = x  | 
304  | 
  | dest_TVar T = raise TYPE ("dest_TVar", [T], []);
 | 
|
| 
6033
 
c8c69a4a7762
moved dest_Type to term.ML from HOL/Tools/primrec_package
 
paulson 
parents: 
5986 
diff
changeset
 | 
305  | 
|
| 16537 | 306  | 
|
| 0 | 307  | 
(** Discriminators **)  | 
308  | 
||
| 7318 | 309  | 
fun is_Bound (Bound _) = true  | 
310  | 
| is_Bound _ = false;  | 
|
311  | 
||
| 0 | 312  | 
fun is_Const (Const _) = true  | 
313  | 
| is_Const _ = false;  | 
|
314  | 
||
315  | 
fun is_Free (Free _) = true  | 
|
316  | 
| is_Free _ = false;  | 
|
317  | 
||
318  | 
fun is_Var (Var _) = true  | 
|
319  | 
| is_Var _ = false;  | 
|
320  | 
||
| 80675 | 321  | 
fun eq_Const_name (Const (a, _), Const (b, _)) = a = b  | 
322  | 
| eq_Const_name _ = false;  | 
|
323  | 
||
| 16537 | 324  | 
|
| 0 | 325  | 
(** Destructors **)  | 
326  | 
||
327  | 
fun dest_Const (Const x) = x  | 
|
328  | 
  | dest_Const t = raise TERM("dest_Const", [t]);
 | 
|
329  | 
||
| 80635 | 330  | 
val dest_Const_name = #1 o dest_Const;  | 
331  | 
val dest_Const_type = #2 o dest_Const;  | 
|
332  | 
||
| 0 | 333  | 
fun dest_Free (Free x) = x  | 
334  | 
  | dest_Free t = raise TERM("dest_Free", [t]);
 | 
|
335  | 
||
336  | 
fun dest_Var (Var x) = x  | 
|
337  | 
  | dest_Var t = raise TERM("dest_Var", [t]);
 | 
|
338  | 
||
| 35227 | 339  | 
fun dest_comb (t1 $ t2) = (t1, t2)  | 
340  | 
  | dest_comb t = raise TERM("dest_comb", [t]);
 | 
|
341  | 
||
| 0 | 342  | 
|
| 40841 | 343  | 
fun domain_type (Type ("fun", [T, _])) = T;
 | 
344  | 
||
345  | 
fun range_type (Type ("fun", [_, U])) = U;
 | 
|
| 4064 | 346  | 
|
| 40840 | 347  | 
fun dest_funT (Type ("fun", [T, U])) = (T, U)
 | 
348  | 
  | dest_funT T = raise TYPE ("dest_funT", [T], []);
 | 
|
349  | 
||
350  | 
||
| 63611 | 351  | 
(*maps [T1,...,Tn]--->T to the list [T1,T2,...,Tn]*)  | 
| 40841 | 352  | 
fun binder_types (Type ("fun", [T, U])) = T :: binder_types U
 | 
353  | 
| binder_types _ = [];  | 
|
| 0 | 354  | 
|
| 63611 | 355  | 
(*maps [T1,...,Tn]--->T to T*)  | 
| 40841 | 356  | 
fun body_type (Type ("fun", [_, U])) = body_type U
 | 
357  | 
| body_type T = T;  | 
|
| 0 | 358  | 
|
| 63611 | 359  | 
(*maps [T1,...,Tn]--->T to ([T1,T2,...,Tn], T)*)  | 
| 40841 | 360  | 
fun strip_type T = (binder_types T, body_type T);  | 
| 0 | 361  | 
|
362  | 
||
363  | 
(*Compute the type of the term, checking that combinations are well-typed  | 
|
364  | 
Ts = [T0,T1,...] holds types of bound variables 0, 1, ...*)  | 
|
365  | 
fun type_of1 (Ts, Const (_,T)) = T  | 
|
366  | 
| type_of1 (Ts, Free (_,T)) = T  | 
|
| 30146 | 367  | 
| type_of1 (Ts, Bound i) = (nth Ts i  | 
| 43278 | 368  | 
        handle General.Subscript => raise TYPE("type_of: bound variable", [], [Bound i]))
 | 
| 0 | 369  | 
| type_of1 (Ts, Var (_,T)) = T  | 
370  | 
| type_of1 (Ts, Abs (_,T,body)) = T --> type_of1(T::Ts, body)  | 
|
| 13000 | 371  | 
| type_of1 (Ts, f$u) =  | 
| 0 | 372  | 
let val U = type_of1(Ts,u)  | 
373  | 
and T = type_of1(Ts,f)  | 
|
374  | 
in case T of  | 
|
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
375  | 
            Type("fun",[T1,T2]) =>
 | 
| 
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
376  | 
if T1=U then T2 else raise TYPE  | 
| 
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
377  | 
                    ("type_of: type mismatch in application", [T1,U], [f$u])
 | 
| 13000 | 378  | 
| _ => raise TYPE  | 
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
379  | 
                    ("type_of: function type is expected in application",
 | 
| 
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
380  | 
[T,U], [f$u])  | 
| 0 | 381  | 
end;  | 
382  | 
||
383  | 
fun type_of t : typ = type_of1 ([],t);  | 
|
384  | 
||
| 
73351
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
385  | 
(*Determine the type of a term, with minimal checking*)  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
386  | 
local  | 
| 61 | 387  | 
|
| 
73351
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
388  | 
fun fastype_of_term Ts (Abs (_, T, t)) = T --> fastype_of_term (T :: Ts) t  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
389  | 
| fastype_of_term Ts (t $ _) = range_type_of Ts t  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
390  | 
| fastype_of_term Ts a = fastype_of_atom Ts a  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
391  | 
and fastype_of_atom _ (Const (_, T)) = T  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
392  | 
| fastype_of_atom _ (Free (_, T)) = T  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
393  | 
| fastype_of_atom _ (Var (_, T)) = T  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
394  | 
| fastype_of_atom Ts (Bound i) = fastype_of_bound Ts i  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
395  | 
and fastype_of_bound (T :: Ts) i = if i = 0 then T else fastype_of_bound Ts (i - 1)  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
396  | 
  | fastype_of_bound [] i = raise TERM ("fastype_of: Bound", [Bound i])
 | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
397  | 
and range_type_of Ts (Abs (_, T, u)) = fastype_of_term (T :: Ts) u  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
398  | 
| range_type_of Ts (t $ u) = range_type_ofT (t $ u) (range_type_of Ts t)  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
399  | 
| range_type_of Ts a = range_type_ofT a (fastype_of_atom Ts a)  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
400  | 
and range_type_ofT _ (Type ("fun", [_, T])) = T
 | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
401  | 
  | range_type_ofT t _ = raise TERM ("fastype_of: expected function type", [t]);
 | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
402  | 
|
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
403  | 
in  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
404  | 
|
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
405  | 
val fastype_of1 = uncurry fastype_of_term;  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
406  | 
val fastype_of = fastype_of_term [];  | 
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
407  | 
|
| 
 
88dd8a6a42ba
slightly more efficient Term.fastype_of (only little impact in regular applications);
 
wenzelm 
parents: 
67721 
diff
changeset
 | 
408  | 
end;  | 
| 0 | 409  | 
|
| 16678 | 410  | 
(*Determine the argument type of a function*)  | 
| 22908 | 411  | 
fun argument_type_of tm k =  | 
| 16678 | 412  | 
let  | 
413  | 
    fun argT i (Type ("fun", [T, U])) = if i = 0 then T else argT (i - 1) U
 | 
|
414  | 
      | argT _ T = raise TYPE ("argument_type_of", [T], []);
 | 
|
415  | 
||
416  | 
fun arg 0 _ (Abs (_, T, _)) = T  | 
|
417  | 
| arg i Ts (Abs (_, T, t)) = arg (i - 1) (T :: Ts) t  | 
|
418  | 
| arg i Ts (t $ _) = arg (i + 1) Ts t  | 
|
419  | 
| arg i Ts a = argT i (fastype_of1 (Ts, a));  | 
|
| 22908 | 420  | 
in arg k [] tm end;  | 
| 16678 | 421  | 
|
| 0 | 422  | 
|
| 
46219
 
426ed18eba43
discontinued old-style Term.list_abs in favour of plain Term.abs;
 
wenzelm 
parents: 
46218 
diff
changeset
 | 
423  | 
fun abs (x, T) t = Abs (x, T, t);  | 
| 10806 | 424  | 
|
| 79228 | 425  | 
fun strip_abs (Abs (a, T, t)) = strip_abs t |>> cons (a, T)  | 
| 18927 | 426  | 
| strip_abs t = ([], t);  | 
427  | 
||
| 79228 | 428  | 
fun strip_abs_body (Abs (_, _, t)) = strip_abs_body t  | 
429  | 
| strip_abs_body t = t;  | 
|
| 0 | 430  | 
|
| 79228 | 431  | 
fun strip_abs_vars (Abs (a, T, t)) = strip_abs_vars t |> cons (a, T)  | 
432  | 
| strip_abs_vars _ = [];  | 
|
| 0 | 433  | 
|
434  | 
||
435  | 
fun strip_qnt_body qnt =  | 
|
| 79228 | 436  | 
let  | 
437  | 
fun strip (tm as Const (c, _) $ Abs (_, _, t)) = if c = qnt then strip t else tm  | 
|
438  | 
| strip t = t;  | 
|
439  | 
in strip end;  | 
|
| 0 | 440  | 
|
441  | 
fun strip_qnt_vars qnt =  | 
|
| 79228 | 442  | 
let  | 
443  | 
fun strip (Const (c, _) $ Abs (a, T, t)) = if c = qnt then (a, T) :: strip t else []  | 
|
444  | 
| strip _ = [];  | 
|
445  | 
in strip end;  | 
|
| 0 | 446  | 
|
447  | 
||
| 63611 | 448  | 
(*maps (f, [t1,...,tn]) to f(t1,...,tn)*)  | 
| 15570 | 449  | 
val list_comb : term * term list -> term = Library.foldl (op $);  | 
| 0 | 450  | 
|
451  | 
||
| 63611 | 452  | 
(*maps f(t1,...,tn) to (f, [t1,...,tn]) ; naturally tail-recursive*)  | 
| 79440 | 453  | 
fun strip_comb tm =  | 
454  | 
let  | 
|
455  | 
fun strip (f $ t, ts) = strip (f, t :: ts)  | 
|
456  | 
| strip res = res;  | 
|
457  | 
in strip (tm, []) end;  | 
|
| 0 | 458  | 
|
| 79440 | 459  | 
val args_of =  | 
460  | 
let  | 
|
461  | 
fun args (f $ t) ts = args f (t :: ts)  | 
|
462  | 
| args _ ts = ts;  | 
|
463  | 
in build o args end;  | 
|
| 0 | 464  | 
|
| 63611 | 465  | 
(*maps f(t1,...,tn) to f , which is never a combination*)  | 
| 79440 | 466  | 
fun head_of (f $ _) = head_of f  | 
467  | 
| head_of t = t;  | 
|
| 0 | 468  | 
|
| 16599 | 469  | 
(*number of atoms and abstractions in a term*)  | 
470  | 
fun size_of_term tm =  | 
|
471  | 
let  | 
|
| 
30144
 
56ae4893e8ae
tuned/unified size_of_term and size_of_typ, eliminated obsolete foldl;
 
wenzelm 
parents: 
29882 
diff
changeset
 | 
472  | 
fun add_size (t $ u) n = add_size t (add_size u n)  | 
| 
 
56ae4893e8ae
tuned/unified size_of_term and size_of_typ, eliminated obsolete foldl;
 
wenzelm 
parents: 
29882 
diff
changeset
 | 
473  | 
| add_size (Abs (_ ,_, t)) n = add_size t (n + 1)  | 
| 
 
56ae4893e8ae
tuned/unified size_of_term and size_of_typ, eliminated obsolete foldl;
 
wenzelm 
parents: 
29882 
diff
changeset
 | 
474  | 
| add_size _ n = n + 1;  | 
| 
 
56ae4893e8ae
tuned/unified size_of_term and size_of_typ, eliminated obsolete foldl;
 
wenzelm 
parents: 
29882 
diff
changeset
 | 
475  | 
in add_size tm 0 end;  | 
| 0 | 476  | 
|
| 
30144
 
56ae4893e8ae
tuned/unified size_of_term and size_of_typ, eliminated obsolete foldl;
 
wenzelm 
parents: 
29882 
diff
changeset
 | 
477  | 
(*number of atoms and constructors in a type*)  | 
| 
29882
 
29154e67731d
New command find_consts searching for constants by type (by Timothy Bourke).
 
kleing 
parents: 
29286 
diff
changeset
 | 
478  | 
fun size_of_typ ty =  | 
| 
 
29154e67731d
New command find_consts searching for constants by type (by Timothy Bourke).
 
kleing 
parents: 
29286 
diff
changeset
 | 
479  | 
let  | 
| 
30144
 
56ae4893e8ae
tuned/unified size_of_term and size_of_typ, eliminated obsolete foldl;
 
wenzelm 
parents: 
29882 
diff
changeset
 | 
480  | 
fun add_size (Type (_, tys)) n = fold add_size tys (n + 1)  | 
| 
 
56ae4893e8ae
tuned/unified size_of_term and size_of_typ, eliminated obsolete foldl;
 
wenzelm 
parents: 
29882 
diff
changeset
 | 
481  | 
| add_size _ n = n + 1;  | 
| 
 
56ae4893e8ae
tuned/unified size_of_term and size_of_typ, eliminated obsolete foldl;
 
wenzelm 
parents: 
29882 
diff
changeset
 | 
482  | 
in add_size ty 0 end;  | 
| 
29882
 
29154e67731d
New command find_consts searching for constants by type (by Timothy Bourke).
 
kleing 
parents: 
29286 
diff
changeset
 | 
483  | 
|
| 79409 | 484  | 
|
485  | 
(* map types and terms *)  | 
|
486  | 
||
487  | 
fun map_atyps_same f =  | 
|
488  | 
let  | 
|
489  | 
fun typ (Type (a, Ts)) = Type (a, Same.map typ Ts)  | 
|
490  | 
| typ T = f T;  | 
|
491  | 
in typ end;  | 
|
| 18847 | 492  | 
|
| 79409 | 493  | 
fun map_aterms_same f =  | 
494  | 
let  | 
|
495  | 
fun term (Abs (x, T, t)) = Abs (x, T, term t)  | 
|
496  | 
| term (t $ u) =  | 
|
497  | 
(term t $ Same.commit term u  | 
|
498  | 
handle Same.SAME => t $ term u)  | 
|
499  | 
| term a = f a;  | 
|
500  | 
in term end;  | 
|
| 
949
 
83c588d6fee9
Changed treatment of during type inference internally generated type
 
nipkow 
parents: 
728 
diff
changeset
 | 
501  | 
|
| 79409 | 502  | 
fun map_types_same f =  | 
| 16678 | 503  | 
let  | 
| 79450 | 504  | 
fun term (Const (c, T)) = Const (c, f T)  | 
505  | 
| term (Free (x, T)) = Free (x, f T)  | 
|
| 79409 | 506  | 
| term (Var (xi, T)) = Var (xi, f T)  | 
507  | 
| term (Bound _) = raise Same.SAME  | 
|
508  | 
| term (Abs (x, T, t)) =  | 
|
509  | 
(Abs (x, f T, Same.commit term t)  | 
|
510  | 
handle Same.SAME => Abs (x, T, term t))  | 
|
511  | 
| term (t $ u) =  | 
|
512  | 
(term t $ Same.commit term u  | 
|
513  | 
handle Same.SAME => t $ term u);  | 
|
514  | 
in term end;  | 
|
515  | 
||
516  | 
val map_atyps = Same.commit o map_atyps_same;  | 
|
517  | 
val map_aterms = Same.commit o map_aterms_same;  | 
|
518  | 
val map_types = Same.commit o map_types_same;  | 
|
519  | 
||
520  | 
fun map_type_tvar f = map_atyps (fn TVar x => f x | _ => raise Same.SAME);  | 
|
521  | 
fun map_type_tfree f = map_atyps (fn TFree x => f x | _ => raise Same.SAME);  | 
|
| 0 | 522  | 
|
523  | 
||
| 16943 | 524  | 
(* fold types and terms *)  | 
525  | 
||
526  | 
fun fold_atyps f (Type (_, Ts)) = fold (fold_atyps f) Ts  | 
|
527  | 
| fold_atyps f T = f T;  | 
|
528  | 
||
| 35986 | 529  | 
fun fold_atyps_sorts f =  | 
530  | 
fold_atyps (fn T as TFree (_, S) => f (T, S) | T as TVar (_, S) => f (T, S));  | 
|
531  | 
||
| 16943 | 532  | 
fun fold_aterms f (t $ u) = fold_aterms f t #> fold_aterms f u  | 
533  | 
| fold_aterms f (Abs (_, _, t)) = fold_aterms f t  | 
|
534  | 
| fold_aterms f a = f a;  | 
|
535  | 
||
536  | 
fun fold_term_types f (t as Const (_, T)) = f t T  | 
|
537  | 
| fold_term_types f (t as Free (_, T)) = f t T  | 
|
538  | 
| fold_term_types f (t as Var (_, T)) = f t T  | 
|
539  | 
| fold_term_types f (Bound _) = I  | 
|
540  | 
| fold_term_types f (t as Abs (_, T, b)) = f t T #> fold_term_types f b  | 
|
541  | 
| fold_term_types f (t $ u) = fold_term_types f t #> fold_term_types f u;  | 
|
542  | 
||
543  | 
fun fold_types f = fold_term_types (K f);  | 
|
544  | 
||
| 24483 | 545  | 
fun replace_types (Const (c, _)) (T :: Ts) = (Const (c, T), Ts)  | 
546  | 
| replace_types (Free (x, _)) (T :: Ts) = (Free (x, T), Ts)  | 
|
547  | 
| replace_types (Var (xi, _)) (T :: Ts) = (Var (xi, T), Ts)  | 
|
548  | 
| replace_types (Bound i) Ts = (Bound i, Ts)  | 
|
549  | 
| replace_types (Abs (x, _, b)) (T :: Ts) =  | 
|
550  | 
let val (b', Ts') = replace_types b Ts  | 
|
551  | 
in (Abs (x, T, b'), Ts') end  | 
|
552  | 
| replace_types (t $ u) Ts =  | 
|
553  | 
let  | 
|
554  | 
val (t', Ts') = replace_types t Ts;  | 
|
555  | 
val (u', Ts'') = replace_types u Ts';  | 
|
556  | 
in (t' $ u', Ts'') end;  | 
|
557  | 
||
558  | 
fun burrow_types f ts =  | 
|
559  | 
let  | 
|
| 
49674
 
dbadb4d03cbc
report sort assignment of visible type variables;
 
wenzelm 
parents: 
48263 
diff
changeset
 | 
560  | 
val Ts = rev ((fold o fold_types) cons ts []);  | 
| 24483 | 561  | 
val Ts' = f Ts;  | 
562  | 
val (ts', []) = fold_map replace_types ts Ts';  | 
|
563  | 
in ts' end;  | 
|
564  | 
||
| 16943 | 565  | 
(*collect variables*)  | 
| 
29257
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
566  | 
val add_tvar_namesT = fold_atyps (fn TVar (xi, _) => insert (op =) xi | _ => I);  | 
| 
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
567  | 
val add_tvar_names = fold_types add_tvar_namesT;  | 
| 16943 | 568  | 
val add_tvarsT = fold_atyps (fn TVar v => insert (op =) v | _ => I);  | 
569  | 
val add_tvars = fold_types add_tvarsT;  | 
|
| 
29257
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
570  | 
val add_var_names = fold_aterms (fn Var (xi, _) => insert (op =) xi | _ => I);  | 
| 16943 | 571  | 
val add_vars = fold_aterms (fn Var v => insert (op =) v | _ => I);  | 
| 33697 | 572  | 
val add_tfree_namesT = fold_atyps (fn TFree (a, _) => insert (op =) a | _ => I);  | 
| 
29257
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
573  | 
val add_tfree_names = fold_types add_tfree_namesT;  | 
| 16943 | 574  | 
val add_tfreesT = fold_atyps (fn TFree v => insert (op =) v | _ => I);  | 
575  | 
val add_tfrees = fold_types add_tfreesT;  | 
|
| 
29257
 
660234d959f7
provide canonical add_tvar_namesT, add_tvar_names, add_tfree_namesT, add_tfree_names, add_free_names;
 
wenzelm 
parents: 
29256 
diff
changeset
 | 
576  | 
val add_free_names = fold_aterms (fn Free (x, _) => insert (op =) x | _ => I);  | 
| 16943 | 577  | 
val add_frees = fold_aterms (fn Free v => insert (op =) v | _ => I);  | 
| 29286 | 578  | 
val add_const_names = fold_aterms (fn Const (c, _) => insert (op =) c | _ => I);  | 
579  | 
val add_consts = fold_aterms (fn Const c => insert (op =) c | _ => I);  | 
|
| 81505 | 580  | 
val declare_tfree_namesT = fold_atyps (fn TFree (a, _) => Name.declare a | _ => I);  | 
581  | 
val declare_tfree_names = fold_types declare_tfree_namesT;  | 
|
| 81515 | 582  | 
fun declare_tvar_namesT pred = fold_atyps (fn TVar ((a, i), _) => pred i ? Name.declare a | _ => I);  | 
583  | 
val declare_tvar_names = fold_types o declare_tvar_namesT;  | 
|
| 81505 | 584  | 
val declare_free_names = fold_aterms (fn Free (x, _) => Name.declare x | _ => I);  | 
| 81515 | 585  | 
fun declare_var_names pred = fold_aterms (fn Var ((x, i), _) => pred i ? Name.declare x | _ => I);  | 
| 16943 | 586  | 
|
| 25050 | 587  | 
(*extra type variables in a term, not covered by its type*)  | 
588  | 
fun hidden_polymorphism t =  | 
|
| 21682 | 589  | 
let  | 
| 25050 | 590  | 
val T = fastype_of t;  | 
| 21682 | 591  | 
val tvarsT = add_tvarsT T [];  | 
592  | 
val extra_tvars = fold_types (fold_atyps  | 
|
593  | 
(fn TVar v => if member (op =) tvarsT v then I else insert (op =) v | _ => I)) t [];  | 
|
594  | 
in extra_tvars end;  | 
|
595  | 
||
| 16943 | 596  | 
|
| 29278 | 597  | 
(* renaming variables *)  | 
598  | 
||
599  | 
fun declare_term_names tm =  | 
|
600  | 
fold_aterms  | 
|
| 
30364
 
577edc39b501
moved basic algebra of long names from structure NameSpace to Long_Name;
 
wenzelm 
parents: 
30285 
diff
changeset
 | 
601  | 
(fn Const (a, _) => Name.declare (Long_Name.base_name a)  | 
| 29278 | 602  | 
| Free (a, _) => Name.declare a  | 
603  | 
| _ => I) tm #>  | 
|
| 81505 | 604  | 
declare_tfree_names tm;  | 
| 29278 | 605  | 
|
606  | 
fun variant_frees t frees =  | 
|
| 
81506
 
f76a5849b570
tuned: more standard Name.build_context, although that is a bit longer;
 
wenzelm 
parents: 
81505 
diff
changeset
 | 
607  | 
#1 (fold_map Name.variant (map fst frees) (Name.build_context (declare_term_names t))) ~~  | 
| 
 
f76a5849b570
tuned: more standard Name.build_context, although that is a bit longer;
 
wenzelm 
parents: 
81505 
diff
changeset
 | 
608  | 
map #2 frees;  | 
| 29278 | 609  | 
|
610  | 
fun rename_wrt_term t frees = rev (variant_frees t frees); (*reversed result!*)  | 
|
611  | 
||
612  | 
||
| 79411 | 613  | 
(* sorts *)  | 
614  | 
||
615  | 
fun smash_sortsT_same S' =  | 
|
616  | 
map_atyps_same  | 
|
617  | 
(fn TFree (x, S) => if S = S' then raise Same.SAME else TFree (x, S')  | 
|
618  | 
| TVar (xi, S) => if S = S' then raise Same.SAME else TVar (xi, S'));  | 
|
619  | 
||
| 79439 | 620  | 
val smash_sortsT = Same.commit o smash_sortsT_same;  | 
621  | 
val smash_sorts = map_types o smash_sortsT_same;  | 
|
622  | 
||
| 79411 | 623  | 
val strip_sortsT_same = smash_sortsT_same [];  | 
624  | 
val strip_sortsT = Same.commit strip_sortsT_same;  | 
|
625  | 
val strip_sorts = map_types strip_sortsT_same;  | 
|
626  | 
||
627  | 
||
| 25050 | 628  | 
|
| 
29269
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
629  | 
(** Comparing terms **)  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
630  | 
|
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
631  | 
(* variables *)  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
632  | 
|
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
633  | 
fun eq_ix ((x, i): indexname, (y, j)) = i = j andalso x = y;  | 
| 16537 | 634  | 
|
| 
29269
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
635  | 
fun eq_tvar ((xi, S: sort), (xi', S')) = eq_ix (xi, xi') andalso S = S';  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
636  | 
fun eq_var ((xi, T: typ), (xi', T')) = eq_ix (xi, xi') andalso T = T';  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
637  | 
|
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
638  | 
|
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
639  | 
(* alpha equivalence *)  | 
| 20511 | 640  | 
|
641  | 
fun tm1 aconv tm2 =  | 
|
642  | 
pointer_eq (tm1, tm2) orelse  | 
|
643  | 
(case (tm1, tm2) of  | 
|
644  | 
(t1 $ u1, t2 $ u2) => t1 aconv t2 andalso u1 aconv u2  | 
|
645  | 
| (Abs (_, T1, t1), Abs (_, T2, t2)) => t1 aconv t2 andalso T1 = T2  | 
|
646  | 
| (a1, a2) => a1 = a2);  | 
|
647  | 
||
| 
33537
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
648  | 
fun aconv_untyped (tm1, tm2) =  | 
| 
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
649  | 
pointer_eq (tm1, tm2) orelse  | 
| 
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
650  | 
(case (tm1, tm2) of  | 
| 
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
651  | 
(t1 $ u1, t2 $ u2) => aconv_untyped (t1, t2) andalso aconv_untyped (u1, u2)  | 
| 
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
652  | 
| (Abs (_, _, t1), Abs (_, _, t2)) => aconv_untyped (t1, t2)  | 
| 
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
653  | 
| (Const (a, _), Const (b, _)) => a = b  | 
| 
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
654  | 
| (Free (x, _), Free (y, _)) => x = y  | 
| 
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
655  | 
| (Var (xi, _), Var (yj, _)) => xi = yj  | 
| 
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
656  | 
| (Bound i, Bound j) => i = j  | 
| 
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
657  | 
| _ => false);  | 
| 
 
06c87d2c5b5a
locale_const/target_notation: uniform use of Term.aconv_untyped;
 
wenzelm 
parents: 
33063 
diff
changeset
 | 
658  | 
|
| 20511 | 659  | 
|
| 
29269
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
660  | 
(*A fast unification filter: true unless the two terms cannot be unified.  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
661  | 
Terms must be NORMAL. Treats all Vars as distinct. *)  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
662  | 
fun could_unify (t, u) =  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
663  | 
let  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
664  | 
fun matchrands (f $ t) (g $ u) = could_unify (t, u) andalso matchrands f g  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
665  | 
| matchrands _ _ = true;  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
666  | 
in  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
667  | 
case (head_of t, head_of u) of  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
668  | 
(_, Var _) => true  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
669  | 
| (Var _, _) => true  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
670  | 
| (Const (a, _), Const (b, _)) => a = b andalso matchrands t u  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
671  | 
| (Free (a, _), Free (b, _)) => a = b andalso matchrands t u  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
672  | 
| (Bound i, Bound j) => i = j andalso matchrands t u  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
673  | 
| (Abs _, _) => true (*because of possible eta equality*)  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
674  | 
| (_, Abs _) => true  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
675  | 
| _ => false  | 
| 
 
5c25a2012975
moved term order operations to structure TermOrd (cf. Pure/term_ord.ML);
 
wenzelm 
parents: 
29265 
diff
changeset
 | 
676  | 
end;  | 
| 16678 | 677  | 
|
| 16570 | 678  | 
|
| 16537 | 679  | 
|
| 0 | 680  | 
(** Connectives of higher order logic **)  | 
681  | 
||
| 24850 | 682  | 
fun aT S = TFree (Name.aT, S);  | 
| 19394 | 683  | 
|
| 375 | 684  | 
fun itselfT ty = Type ("itself", [ty]);
 | 
| 24850 | 685  | 
val a_itselfT = itselfT (TFree (Name.aT, []));  | 
| 375 | 686  | 
|
| 
46217
 
7b19666f0e3d
renamed Term.all to Logic.all_const, in accordance to HOLogic.all_const;
 
wenzelm 
parents: 
46215 
diff
changeset
 | 
687  | 
val propT : typ = Type ("prop",[]);
 | 
| 0 | 688  | 
|
| 67721 | 689  | 
(*maps \<And>x1...xn. t to t*)  | 
| 60311 | 690  | 
fun strip_all_body (Const ("Pure.all", _) $ Abs (_, _, t)) = strip_all_body t
 | 
691  | 
| strip_all_body t = t;  | 
|
| 0 | 692  | 
|
| 67721 | 693  | 
(*maps \<And>x1...xn. t to [x1, ..., xn]*)  | 
| 60311 | 694  | 
fun strip_all_vars (Const ("Pure.all", _) $ Abs (a, T, t)) = (a, T) :: strip_all_vars t
 | 
695  | 
| strip_all_vars t = [];  | 
|
| 0 | 696  | 
|
697  | 
(*increments a term's non-local bound variables  | 
|
698  | 
required when moving a term within abstractions  | 
|
699  | 
inc is increment for bound variables  | 
|
700  | 
lev is level at which a bound variable is considered 'loose'*)  | 
|
| 
79172
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
701  | 
fun incr_bv_same inc =  | 
| 
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
702  | 
if inc = 0 then fn _ => Same.same  | 
| 
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
703  | 
else  | 
| 
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
704  | 
let  | 
| 79285 | 705  | 
fun term lev (Bound i) =  | 
706  | 
if i >= lev then Bound (i + inc) else raise Same.SAME  | 
|
| 
79172
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
707  | 
| term lev (Abs (a, T, t)) = Abs (a, T, term (lev + 1) t)  | 
| 
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
708  | 
| term lev (t $ u) =  | 
| 79285 | 709  | 
(term lev t $ Same.commit (term lev) u  | 
710  | 
handle Same.SAME => t $ term lev u)  | 
|
| 
79172
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
711  | 
| term _ _ = raise Same.SAME;  | 
| 
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
712  | 
in term end;  | 
| 0 | 713  | 
|
| 
79172
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
714  | 
fun incr_bv inc lev = Same.commit (incr_bv_same inc lev);  | 
| 
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
715  | 
|
| 
 
0bea00f77ba3
minor performance tuning: regular Same.operation;
 
wenzelm 
parents: 
79170 
diff
changeset
 | 
716  | 
fun incr_boundvars inc = incr_bv inc 0;  | 
| 0 | 717  | 
|
| 79243 | 718  | 
(*Scan a pair of terms; while they are similar, accumulate corresponding bound vars*)  | 
719  | 
fun match_bvs (Abs (x, _, s), Abs (y, _, t)) =  | 
|
720  | 
(x <> "" andalso y <> "") ? cons (x, y) #> match_bvs (s, t)  | 
|
721  | 
| match_bvs (f $ s, g $ t) = match_bvs (s, t) #> match_bvs (f, g)  | 
|
722  | 
| match_bvs _ = I;  | 
|
| 12981 | 723  | 
|
724  | 
(* strip abstractions created by parameters *)  | 
|
| 79243 | 725  | 
val match_bvars = apply2 strip_abs_body #> match_bvs;  | 
| 12981 | 726  | 
|
| 79244 | 727  | 
fun map_abs_vars_same rename =  | 
728  | 
let  | 
|
729  | 
fun term (Abs (x, T, t)) =  | 
|
730  | 
let val y = rename x  | 
|
731  | 
in if x = y then Abs (x, T, term t) else Abs (y, T, Same.commit term t) end  | 
|
732  | 
| term (t $ u) = (term t $ Same.commit term u handle Same.SAME => t $ term u)  | 
|
733  | 
| term _ = raise Same.SAME;  | 
|
734  | 
in term end;  | 
|
735  | 
||
736  | 
fun map_abs_vars rename = Same.commit (map_abs_vars_same rename);  | 
|
| 22031 | 737  | 
|
| 12981 | 738  | 
fun rename_abs pat obj t =  | 
739  | 
let  | 
|
| 79250 | 740  | 
val renaming = Symtab.make_distinct (match_bvs (pat, obj) []);  | 
741  | 
fun rename x = perhaps (Symtab.lookup renaming) x;  | 
|
742  | 
in if Symtab.forall (op =) renaming then NONE else Same.catch (map_abs_vars_same rename) t end;  | 
|
| 0 | 743  | 
|
744  | 
(*Accumulate all 'loose' bound vars referring to level 'lev' or beyond.  | 
|
745  | 
(Bound 0) is loose at level 0 *)  | 
|
| 13000 | 746  | 
fun add_loose_bnos (Bound i, lev, js) =  | 
| 20854 | 747  | 
if i<lev then js else insert (op =) (i - lev) js  | 
| 0 | 748  | 
| add_loose_bnos (Abs (_,_,t), lev, js) = add_loose_bnos (t, lev+1, js)  | 
749  | 
| add_loose_bnos (f$t, lev, js) =  | 
|
| 13000 | 750  | 
add_loose_bnos (f, lev, add_loose_bnos (t, lev, js))  | 
| 0 | 751  | 
| add_loose_bnos (_, _, js) = js;  | 
752  | 
||
753  | 
fun loose_bnos t = add_loose_bnos (t, 0, []);  | 
|
754  | 
||
755  | 
(* loose_bvar(t,k) iff t contains a 'loose' bound variable referring to  | 
|
756  | 
level k or beyond. *)  | 
|
757  | 
fun loose_bvar(Bound i,k) = i >= k  | 
|
758  | 
| loose_bvar(f$t, k) = loose_bvar(f,k) orelse loose_bvar(t,k)  | 
|
759  | 
| loose_bvar(Abs(_,_,t),k) = loose_bvar(t,k+1)  | 
|
760  | 
| loose_bvar _ = false;  | 
|
761  | 
||
| 2792 | 762  | 
fun loose_bvar1(Bound i,k) = i = k  | 
763  | 
| loose_bvar1(f$t, k) = loose_bvar1(f,k) orelse loose_bvar1(t,k)  | 
|
764  | 
| loose_bvar1(Abs(_,_,t),k) = loose_bvar1(t,k+1)  | 
|
765  | 
| loose_bvar1 _ = false;  | 
|
| 0 | 766  | 
|
| 
42083
 
e1209fc7ecdc
added Term.is_open and Term.is_dependent convenience, to cover common situations of loose bounds;
 
wenzelm 
parents: 
40844 
diff
changeset
 | 
767  | 
fun is_open t = loose_bvar (t, 0);  | 
| 
 
e1209fc7ecdc
added Term.is_open and Term.is_dependent convenience, to cover common situations of loose bounds;
 
wenzelm 
parents: 
40844 
diff
changeset
 | 
768  | 
fun is_dependent t = loose_bvar1 (t, 0);  | 
| 
 
e1209fc7ecdc
added Term.is_open and Term.is_dependent convenience, to cover common situations of loose bounds;
 
wenzelm 
parents: 
40844 
diff
changeset
 | 
769  | 
|
| 0 | 770  | 
(*Substitute arguments for loose bound variables.  | 
771  | 
Beta-reduction of arg(n-1)...arg0 into t replacing (Bound i) with (argi).  | 
|
| 67721 | 772  | 
Note that for ((\<lambda>x y. c) a b), the bound vars in c are x=1 and y=0  | 
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
773  | 
and the appropriate call is subst_bounds([b,a], c) .  | 
| 0 | 774  | 
Loose bound variables >=n are reduced by "n" to  | 
775  | 
compensate for the disappearance of lambdas.  | 
|
776  | 
*)  | 
|
| 79202 | 777  | 
fun subst_bounds_same args =  | 
778  | 
if null args then fn _ => Same.same  | 
|
779  | 
else  | 
|
780  | 
let  | 
|
781  | 
val n = length args;  | 
|
782  | 
fun term lev (Bound i) =  | 
|
| 79282 | 783  | 
if i < lev then raise Same.SAME (*var is locally bound*)  | 
| 79202 | 784  | 
else if i - lev < n then incr_boundvars lev (nth args (i - lev))  | 
| 79282 | 785  | 
else Bound (i - n) (*loose: change it*)  | 
| 79202 | 786  | 
| term lev (Abs (a, T, t)) = Abs (a, T, term (lev + 1) t)  | 
787  | 
| term lev (t $ u) =  | 
|
788  | 
(term lev t $ Same.commit (term lev) u  | 
|
789  | 
handle Same.SAME => t $ term lev u)  | 
|
790  | 
| term _ _ = raise Same.SAME;  | 
|
791  | 
in term end;  | 
|
792  | 
||
| 79198 | 793  | 
fun subst_bounds (args: term list, body) : term =  | 
| 79202 | 794  | 
if null args then body else Same.commit (subst_bounds_same args 0) body;  | 
| 0 | 795  | 
|
| 
2192
 
3bf092b5310b
Optimizations: removal of polymorphic equality; one-argument case
 
paulson 
parents: 
2182 
diff
changeset
 | 
796  | 
(*Special case: one argument*)  | 
| 79198 | 797  | 
fun subst_bound (arg, body) : term =  | 
| 19065 | 798  | 
let  | 
| 79168 | 799  | 
fun term lev (Bound i) =  | 
| 32020 | 800  | 
if i < lev then raise Same.SAME (*var is locally bound*)  | 
| 19065 | 801  | 
else if i = lev then incr_boundvars lev arg  | 
802  | 
else Bound (i - 1) (*loose: change it*)  | 
|
| 79168 | 803  | 
| term lev (Abs (a, T, t)) = Abs (a, T, term (lev + 1) t)  | 
804  | 
| term lev (t $ u) =  | 
|
805  | 
(term lev t $ Same.commit (term lev) u  | 
|
806  | 
handle Same.SAME => t $ term lev u)  | 
|
807  | 
| term _ _ = raise Same.SAME;  | 
|
| 79198 | 808  | 
in Same.commit (term 0) body end;  | 
| 
2192
 
3bf092b5310b
Optimizations: removal of polymorphic equality; one-argument case
 
paulson 
parents: 
2182 
diff
changeset
 | 
809  | 
|
| 0 | 810  | 
(*beta-reduce if possible, else form application*)  | 
| 
2192
 
3bf092b5310b
Optimizations: removal of polymorphic equality; one-argument case
 
paulson 
parents: 
2182 
diff
changeset
 | 
811  | 
fun betapply (Abs(_,_,t), u) = subst_bound (u,t)  | 
| 0 | 812  | 
| betapply (f,u) = f$u;  | 
813  | 
||
| 18183 | 814  | 
val betapplys = Library.foldl betapply;  | 
815  | 
||
| 
14786
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
816  | 
|
| 20109 | 817  | 
(*unfolding abstractions with substitution  | 
818  | 
of bound variables and implicit eta-expansion*)  | 
|
819  | 
fun strip_abs_eta k t =  | 
|
820  | 
let  | 
|
| 
81506
 
f76a5849b570
tuned: more standard Name.build_context, although that is a bit longer;
 
wenzelm 
parents: 
81505 
diff
changeset
 | 
821  | 
val used = Name.build_context (fold_aterms declare_free_names t);  | 
| 20109 | 822  | 
fun strip_abs t (0, used) = (([], t), (0, used))  | 
823  | 
| strip_abs (Abs (v, T, t)) (k, used) =  | 
|
824  | 
let  | 
|
| 
43326
 
47cf4bc789aa
simplified Name.variant -- discontinued builtin fold_map;
 
wenzelm 
parents: 
43324 
diff
changeset
 | 
825  | 
val (v', used') = Name.variant v used;  | 
| 21013 | 826  | 
val t' = subst_bound (Free (v', T), t);  | 
| 20122 | 827  | 
val ((vs, t''), (k', used'')) = strip_abs t' (k - 1, used');  | 
828  | 
in (((v', T) :: vs, t''), (k', used'')) end  | 
|
| 20109 | 829  | 
| strip_abs t (k, used) = (([], t), (k, used));  | 
830  | 
fun expand_eta [] t _ = ([], t)  | 
|
831  | 
| expand_eta (T::Ts) t used =  | 
|
832  | 
let  | 
|
| 
43326
 
47cf4bc789aa
simplified Name.variant -- discontinued builtin fold_map;
 
wenzelm 
parents: 
43324 
diff
changeset
 | 
833  | 
val (v, used') = Name.variant "" used;  | 
| 20122 | 834  | 
val (vs, t') = expand_eta Ts (t $ Free (v, T)) used';  | 
| 20109 | 835  | 
in ((v, T) :: vs, t') end;  | 
836  | 
val ((vs1, t'), (k', used')) = strip_abs t (k, used);  | 
|
| 40844 | 837  | 
val Ts = fst (chop k' (binder_types (fastype_of t')));  | 
| 20109 | 838  | 
val (vs2, t'') = expand_eta Ts t' used';  | 
839  | 
in (vs1 @ vs2, t'') end;  | 
|
840  | 
||
841  | 
||
| 0 | 842  | 
(*Substitute new for free occurrences of old in a term*)  | 
| 29256 | 843  | 
fun subst_free [] = I  | 
| 0 | 844  | 
| subst_free pairs =  | 
| 13000 | 845  | 
let fun substf u =  | 
| 17314 | 846  | 
case AList.lookup (op aconv) pairs u of  | 
| 15531 | 847  | 
SOME u' => u'  | 
848  | 
| NONE => (case u of Abs(a,T,t) => Abs(a, T, substf t)  | 
|
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
849  | 
| t$u' => substf t $ substf u'  | 
| 
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
850  | 
| _ => u)  | 
| 0 | 851  | 
in substf end;  | 
852  | 
||
| 13000 | 853  | 
(*Abstraction of the term "body" over its occurrences of v,  | 
| 0 | 854  | 
which must contain no loose bound variables.  | 
855  | 
The resulting term is ready to become the body of an Abs.*)  | 
|
| 16882 | 856  | 
fun abstract_over (v, body) =  | 
857  | 
let  | 
|
| 79196 | 858  | 
fun term lev tm =  | 
| 16990 | 859  | 
if v aconv tm then Bound lev  | 
| 16882 | 860  | 
else  | 
| 16990 | 861  | 
(case tm of  | 
| 79196 | 862  | 
Abs (a, T, t) => Abs (a, T, term (lev + 1) t)  | 
| 32020 | 863  | 
| t $ u =>  | 
| 79196 | 864  | 
(term lev t $ Same.commit (term lev) u  | 
865  | 
handle Same.SAME => t $ term lev u)  | 
|
| 32020 | 866  | 
| _ => raise Same.SAME);  | 
| 79196 | 867  | 
in Same.commit (term 0) body end;  | 
| 0 | 868  | 
|
| 32198 | 869  | 
fun term_name (Const (x, _)) = Long_Name.base_name x  | 
870  | 
| term_name (Free (x, _)) = x  | 
|
871  | 
| term_name (Var ((x, _), _)) = x  | 
|
872  | 
| term_name _ = Name.uu;  | 
|
873  | 
||
| 
60404
 
422b63ef0147
clarified abstracted term bindings (again, see c8384ff11711);
 
wenzelm 
parents: 
60311 
diff
changeset
 | 
874  | 
fun dependent_lambda_name (x, v) t =  | 
| 
 
422b63ef0147
clarified abstracted term bindings (again, see c8384ff11711);
 
wenzelm 
parents: 
60311 
diff
changeset
 | 
875  | 
let val t' = abstract_over (v, t)  | 
| 
 
422b63ef0147
clarified abstracted term bindings (again, see c8384ff11711);
 
wenzelm 
parents: 
60311 
diff
changeset
 | 
876  | 
in if is_dependent t' then Abs (if x = "" then term_name v else x, fastype_of v, t') else t end;  | 
| 
 
422b63ef0147
clarified abstracted term bindings (again, see c8384ff11711);
 
wenzelm 
parents: 
60311 
diff
changeset
 | 
877  | 
|
| 32198 | 878  | 
fun lambda_name (x, v) t =  | 
879  | 
Abs (if x = "" then term_name v else x, fastype_of v, abstract_over (v, t));  | 
|
880  | 
||
881  | 
fun lambda v t = lambda_name ("", v) t;
 | 
|
| 0 | 882  | 
|
| 44241 | 883  | 
fun absfree (a, T) body = Abs (a, T, abstract_over (Free (a, T), body));  | 
884  | 
fun absdummy T body = Abs (Name.uu_, T, body);  | 
|
| 0 | 885  | 
|
| 16678 | 886  | 
(*Replace the ATOMIC term ti by ui; inst = [(t1,u1), ..., (tn,un)].  | 
| 0 | 887  | 
A simultaneous substitution: [ (a,b), (b,a) ] swaps a and b. *)  | 
| 16678 | 888  | 
fun subst_atomic [] tm = tm  | 
889  | 
| subst_atomic inst tm =  | 
|
890  | 
let  | 
|
891  | 
fun subst (Abs (a, T, body)) = Abs (a, T, subst body)  | 
|
892  | 
| subst (t $ u) = subst t $ subst u  | 
|
| 18942 | 893  | 
| subst t = the_default t (AList.lookup (op aconv) inst t);  | 
| 16678 | 894  | 
in subst tm end;  | 
| 0 | 895  | 
|
| 16678 | 896  | 
(*Replace the ATOMIC type Ti by Ui; inst = [(T1,U1), ..., (Tn,Un)].*)  | 
897  | 
fun typ_subst_atomic [] ty = ty  | 
|
898  | 
| typ_subst_atomic inst ty =  | 
|
899  | 
let  | 
|
900  | 
fun subst (Type (a, Ts)) = Type (a, map subst Ts)  | 
|
| 18942 | 901  | 
| subst T = the_default T (AList.lookup (op = : typ * typ -> bool) inst T);  | 
| 16678 | 902  | 
in subst ty end;  | 
| 15797 | 903  | 
|
| 16678 | 904  | 
fun subst_atomic_types [] tm = tm  | 
| 
20548
 
8ef25fe585a8
renamed Term.map_term_types to Term.map_types (cf. Term.fold_types);
 
wenzelm 
parents: 
20531 
diff
changeset
 | 
905  | 
| subst_atomic_types inst tm = map_types (typ_subst_atomic inst) tm;  | 
| 16678 | 906  | 
|
907  | 
fun typ_subst_TVars [] ty = ty  | 
|
908  | 
| typ_subst_TVars inst ty =  | 
|
909  | 
let  | 
|
910  | 
fun subst (Type (a, Ts)) = Type (a, map subst Ts)  | 
|
| 18942 | 911  | 
| subst (T as TVar (xi, _)) = the_default T (AList.lookup (op =) inst xi)  | 
| 16678 | 912  | 
| subst T = T;  | 
913  | 
in subst ty end;  | 
|
| 0 | 914  | 
|
| 16678 | 915  | 
fun subst_TVars [] tm = tm  | 
| 
20548
 
8ef25fe585a8
renamed Term.map_term_types to Term.map_types (cf. Term.fold_types);
 
wenzelm 
parents: 
20531 
diff
changeset
 | 
916  | 
| subst_TVars inst tm = map_types (typ_subst_TVars inst) tm;  | 
| 0 | 917  | 
|
| 16678 | 918  | 
fun subst_Vars [] tm = tm  | 
919  | 
| subst_Vars inst tm =  | 
|
920  | 
let  | 
|
| 18942 | 921  | 
fun subst (t as Var (xi, _)) = the_default t (AList.lookup (op =) inst xi)  | 
| 16678 | 922  | 
| subst (Abs (a, T, t)) = Abs (a, T, subst t)  | 
923  | 
| subst (t $ u) = subst t $ subst u  | 
|
924  | 
| subst t = t;  | 
|
925  | 
in subst tm end;  | 
|
| 0 | 926  | 
|
| 16678 | 927  | 
fun subst_vars ([], []) tm = tm  | 
928  | 
| subst_vars ([], inst) tm = subst_Vars inst tm  | 
|
929  | 
| subst_vars (instT, inst) tm =  | 
|
930  | 
let  | 
|
931  | 
fun subst (Const (a, T)) = Const (a, typ_subst_TVars instT T)  | 
|
932  | 
| subst (Free (a, T)) = Free (a, typ_subst_TVars instT T)  | 
|
| 32784 | 933  | 
| subst (Var (xi, T)) =  | 
| 17271 | 934  | 
(case AList.lookup (op =) inst xi of  | 
| 16678 | 935  | 
NONE => Var (xi, typ_subst_TVars instT T)  | 
936  | 
| SOME t => t)  | 
|
937  | 
| subst (t as Bound _) = t  | 
|
938  | 
| subst (Abs (a, T, t)) = Abs (a, typ_subst_TVars instT T, subst t)  | 
|
939  | 
| subst (t $ u) = subst t $ subst u;  | 
|
940  | 
in subst tm end;  | 
|
| 0 | 941  | 
|
| 25050 | 942  | 
fun close_schematic_term t =  | 
943  | 
let  | 
|
| 56243 | 944  | 
    val extra_types = map (fn v => Const ("Pure.type", itselfT (TVar v))) (hidden_polymorphism t);
 | 
| 
30285
 
a135bfab6e83
close_schematic_term: uniform order of types/terms;
 
wenzelm 
parents: 
30280 
diff
changeset
 | 
945  | 
val extra_terms = map Var (add_vars t []);  | 
| 
 
a135bfab6e83
close_schematic_term: uniform order of types/terms;
 
wenzelm 
parents: 
30280 
diff
changeset
 | 
946  | 
in fold lambda (extra_terms @ extra_types) t end;  | 
| 25050 | 947  | 
|
948  | 
||
| 0 | 949  | 
|
| 15573 | 950  | 
(** Identifying first-order terms **)  | 
951  | 
||
| 20199 | 952  | 
(*Differs from proofterm/is_fun in its treatment of TVar*)  | 
| 29256 | 953  | 
fun is_funtype (Type ("fun", [_, _])) = true
 | 
| 20199 | 954  | 
| is_funtype _ = false;  | 
955  | 
||
| 15573 | 956  | 
(*Argument Ts is a reverse list of binder types, needed if term t contains Bound vars*)  | 
| 29256 | 957  | 
fun has_not_funtype Ts t = not (is_funtype (fastype_of1 (Ts, t)));  | 
| 15573 | 958  | 
|
| 16537 | 959  | 
(*First order means in all terms of the form f(t1,...,tn) no argument has a  | 
| 16589 | 960  | 
function type. The supplied quantifiers are excluded: their argument always  | 
961  | 
has a function type through a recursive call into its body.*)  | 
|
| 16667 | 962  | 
fun is_first_order quants =  | 
| 16589 | 963  | 
let fun first_order1 Ts (Abs (_,T,body)) = first_order1 (T::Ts) body  | 
| 16667 | 964  | 
| first_order1 Ts (Const(q,_) $ Abs(a,T,body)) =  | 
| 20664 | 965  | 
member (op =) quants q andalso (*it is a known quantifier*)  | 
| 16589 | 966  | 
not (is_funtype T) andalso first_order1 (T::Ts) body  | 
| 16667 | 967  | 
| first_order1 Ts t =  | 
968  | 
case strip_comb t of  | 
|
969  | 
(Var _, ts) => forall (first_order1 Ts andf has_not_funtype Ts) ts  | 
|
970  | 
| (Free _, ts) => forall (first_order1 Ts andf has_not_funtype Ts) ts  | 
|
971  | 
| (Const _, ts) => forall (first_order1 Ts andf has_not_funtype Ts) ts  | 
|
972  | 
| (Bound _, ts) => forall (first_order1 Ts andf has_not_funtype Ts) ts  | 
|
973  | 
| (Abs _, ts) => false (*not in beta-normal form*)  | 
|
974  | 
| _ => error "first_order: unexpected case"  | 
|
| 16589 | 975  | 
in first_order1 [] end;  | 
| 15573 | 976  | 
|
| 16710 | 977  | 
|
| 16990 | 978  | 
(* maximum index of typs and terms *)  | 
| 0 | 979  | 
|
| 16710 | 980  | 
fun maxidx_typ (TVar ((_, j), _)) i = Int.max (i, j)  | 
981  | 
| maxidx_typ (Type (_, Ts)) i = maxidx_typs Ts i  | 
|
982  | 
| maxidx_typ (TFree _) i = i  | 
|
983  | 
and maxidx_typs [] i = i  | 
|
984  | 
| maxidx_typs (T :: Ts) i = maxidx_typs Ts (maxidx_typ T i);  | 
|
| 0 | 985  | 
|
| 16710 | 986  | 
fun maxidx_term (Var ((_, j), T)) i = maxidx_typ T (Int.max (i, j))  | 
987  | 
| maxidx_term (Const (_, T)) i = maxidx_typ T i  | 
|
988  | 
| maxidx_term (Free (_, T)) i = maxidx_typ T i  | 
|
989  | 
| maxidx_term (Bound _) i = i  | 
|
990  | 
| maxidx_term (Abs (_, T, t)) i = maxidx_term t (maxidx_typ T i)  | 
|
991  | 
| maxidx_term (t $ u) i = maxidx_term u (maxidx_term t i);  | 
|
| 0 | 992  | 
|
| 16710 | 993  | 
fun maxidx_of_typ T = maxidx_typ T ~1;  | 
994  | 
fun maxidx_of_typs Ts = maxidx_typs Ts ~1;  | 
|
995  | 
fun maxidx_of_term t = maxidx_term t ~1;  | 
|
| 13665 | 996  | 
|
| 0 | 997  | 
|
998  | 
||
| 
29270
 
0eade173f77e
moved old add_type_XXX, add_term_XXX etc. to structure OldTerm;
 
wenzelm 
parents: 
29269 
diff
changeset
 | 
999  | 
(** misc syntax operations **)  | 
| 0 | 1000  | 
|
| 19909 | 1001  | 
(* substructure *)  | 
| 
4017
 
63878e2587a7
add_typ_classes, add_typ_tycons, add_term_classes, add_term_tycons,
 
wenzelm 
parents: 
3965 
diff
changeset
 | 
1002  | 
|
| 61248 | 1003  | 
fun fold_subtypes f =  | 
1004  | 
let  | 
|
1005  | 
fun iter ty =  | 
|
1006  | 
(case ty of Type (_, Ts) => f ty #> fold iter Ts | _ => f ty);  | 
|
1007  | 
in iter end;  | 
|
1008  | 
||
| 19909 | 1009  | 
fun exists_subtype P =  | 
1010  | 
let  | 
|
1011  | 
fun ex ty = P ty orelse  | 
|
1012  | 
(case ty of Type (_, Ts) => exists ex Ts | _ => false);  | 
|
1013  | 
in ex end;  | 
|
| 13646 | 1014  | 
|
| 20531 | 1015  | 
fun exists_type P =  | 
1016  | 
let  | 
|
1017  | 
fun ex (Const (_, T)) = P T  | 
|
1018  | 
| ex (Free (_, T)) = P T  | 
|
1019  | 
| ex (Var (_, T)) = P T  | 
|
1020  | 
| ex (Bound _) = false  | 
|
1021  | 
| ex (Abs (_, T, t)) = P T orelse ex t  | 
|
1022  | 
| ex (t $ u) = ex t orelse ex u;  | 
|
1023  | 
in ex end;  | 
|
1024  | 
||
| 16943 | 1025  | 
fun exists_subterm P =  | 
1026  | 
let  | 
|
1027  | 
fun ex tm = P tm orelse  | 
|
1028  | 
(case tm of  | 
|
1029  | 
t $ u => ex t orelse ex u  | 
|
1030  | 
| Abs (_, _, t) => ex t  | 
|
1031  | 
| _ => false);  | 
|
1032  | 
in ex end;  | 
|
| 
16108
 
cf468b93a02e
Implement cycle-free overloading, so that definitions cannot harm consistency any more (except of course via interaction with axioms).
 
obua 
parents: 
16035 
diff
changeset
 | 
1033  | 
|
| 
29270
 
0eade173f77e
moved old add_type_XXX, add_term_XXX etc. to structure OldTerm;
 
wenzelm 
parents: 
29269 
diff
changeset
 | 
1034  | 
fun exists_Const P = exists_subterm (fn Const c => P c | _ => false);  | 
| 
 
0eade173f77e
moved old add_type_XXX, add_term_XXX etc. to structure OldTerm;
 
wenzelm 
parents: 
29269 
diff
changeset
 | 
1035  | 
|
| 76047 | 1036  | 
fun is_schematic t =  | 
1037  | 
exists_subterm is_Var t orelse  | 
|
1038  | 
(exists_type o exists_subtype) is_TVar t;  | 
|
1039  | 
||
| 63619 | 1040  | 
|
1041  | 
(* contraction *)  | 
|
1042  | 
||
1043  | 
fun could_beta_contract (Abs _ $ _) = true  | 
|
1044  | 
| could_beta_contract (t $ u) = could_beta_contract t orelse could_beta_contract u  | 
|
1045  | 
| could_beta_contract (Abs (_, _, b)) = could_beta_contract b  | 
|
1046  | 
| could_beta_contract _ = false;  | 
|
1047  | 
||
1048  | 
fun could_eta_contract (Abs (_, _, _ $ Bound 0)) = true  | 
|
1049  | 
| could_eta_contract (Abs (_, _, b)) = could_eta_contract b  | 
|
1050  | 
| could_eta_contract (t $ u) = could_eta_contract t orelse could_eta_contract u  | 
|
1051  | 
| could_eta_contract _ = false;  | 
|
1052  | 
||
| 24671 | 1053  | 
|
| 20199 | 1054  | 
(* dest abstraction *)  | 
| 0 | 1055  | 
|
| 
74525
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1056  | 
(*ASSUMPTION: x is fresh wrt. the current context, but the check  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1057  | 
of used_free merely guards against gross mistakes*)  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1058  | 
|
| 74407 | 1059  | 
fun used_free x =  | 
| 16678 | 1060  | 
let  | 
| 74407 | 1061  | 
fun used (Free (y, _)) = (x = y)  | 
1062  | 
| used (t $ u) = used t orelse used u  | 
|
1063  | 
| used (Abs (_, _, t)) = used t  | 
|
1064  | 
| used _ = false;  | 
|
1065  | 
in used end;  | 
|
1066  | 
||
| 
74525
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1067  | 
exception USED_FREE of string * term;  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1068  | 
|
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1069  | 
fun subst_abs v b = (v, subst_bound (Free v, b));  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1070  | 
|
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1071  | 
fun dest_abs_fresh x t =  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1072  | 
(case t of  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1073  | 
Abs (_, T, b) =>  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1074  | 
if used_free x b then raise USED_FREE (x, t)  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1075  | 
else subst_abs (x, T) b  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1076  | 
  | _ => raise TERM ("dest_abs", [t]));
 | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1077  | 
|
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1078  | 
fun dest_abs_global t =  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1079  | 
(case t of  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1080  | 
Abs (x, T, b) =>  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1081  | 
if used_free x b then  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1082  | 
let  | 
| 81505 | 1083  | 
val used = Name.build_context (declare_free_names b);  | 
| 
74525
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1084  | 
val x' = #1 (Name.variant x used);  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1085  | 
in subst_abs (x', T) b end  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1086  | 
else subst_abs (x, T) b  | 
| 
 
c960bfcb91db
discontinued Term.dest_abs / Logic.dest_all, which are officially superseded by Variable.dest_abs etc., but there are also Term.dest_abs_global to recover existing tools easily;
 
wenzelm 
parents: 
74446 
diff
changeset
 | 
1087  | 
  | _ => raise TERM ("dest_abs", [t]));
 | 
| 16678 | 1088  | 
|
| 20160 | 1089  | 
|
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
1090  | 
(* dummy patterns *)  | 
| 
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
1091  | 
|
| 56241 | 1092  | 
fun dummy_pattern T = Const ("Pure.dummy_pattern", T);
 | 
| 45156 | 1093  | 
val dummy = dummy_pattern dummyT;  | 
1094  | 
val dummy_prop = dummy_pattern propT;  | 
|
| 18253 | 1095  | 
|
| 56241 | 1096  | 
fun is_dummy_pattern (Const ("Pure.dummy_pattern", _)) = true
 | 
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
1097  | 
| is_dummy_pattern _ = false;  | 
| 
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
1098  | 
|
| 
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
1099  | 
fun no_dummy_patterns tm =  | 
| 16787 | 1100  | 
if not (fold_aterms (fn t => fn b => b orelse is_dummy_pattern t) tm false) then tm  | 
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
1101  | 
  else raise TERM ("Illegal occurrence of '_' dummy pattern", [tm]);
 | 
| 
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
1102  | 
|
| 56241 | 1103  | 
fun free_dummy_patterns (Const ("Pure.dummy_pattern", T)) used =
 | 
| 
43329
 
84472e198515
tuned signature: Name.invent and Name.invent_names;
 
wenzelm 
parents: 
43326 
diff
changeset
 | 
1104  | 
let val [x] = Name.invent used Name.uu 1  | 
| 24733 | 1105  | 
in (Free (Name.internal x, T), Name.declare x used) end  | 
1106  | 
| free_dummy_patterns (Abs (x, T, b)) used =  | 
|
1107  | 
let val (b', used') = free_dummy_patterns b used  | 
|
1108  | 
in (Abs (x, T, b'), used') end  | 
|
1109  | 
| free_dummy_patterns (t $ u) used =  | 
|
1110  | 
let  | 
|
1111  | 
val (t', used') = free_dummy_patterns t used;  | 
|
1112  | 
val (u', used'') = free_dummy_patterns u used';  | 
|
1113  | 
in (t' $ u', used'') end  | 
|
1114  | 
| free_dummy_patterns a used = (a, used);  | 
|
1115  | 
||
| 56241 | 1116  | 
fun replace_dummy Ts (Const ("Pure.dummy_pattern", T)) i =
 | 
| 33063 | 1117  | 
      (list_comb (Var (("_dummy_", i), Ts ---> T), map_range Bound (length Ts)), i + 1)
 | 
| 24762 | 1118  | 
| replace_dummy Ts (Abs (x, T, t)) i =  | 
1119  | 
let val (t', i') = replace_dummy (T :: Ts) t i  | 
|
1120  | 
in (Abs (x, T, t'), i') end  | 
|
1121  | 
| replace_dummy Ts (t $ u) i =  | 
|
1122  | 
let  | 
|
1123  | 
val (t', i') = replace_dummy Ts t i;  | 
|
1124  | 
val (u', i'') = replace_dummy Ts u i';  | 
|
1125  | 
in (t' $ u', i'') end  | 
|
1126  | 
| replace_dummy _ a i = (a, i);  | 
|
| 11903 | 1127  | 
|
1128  | 
val replace_dummy_patterns = replace_dummy [];  | 
|
| 
9536
 
b79b002f32ae
added dummy_patternN, no_dummy_patterns, replace_dummy_patterns;
 
wenzelm 
parents: 
9319 
diff
changeset
 | 
1129  | 
|
| 45156 | 1130  | 
fun show_dummy_patterns (Var (("_dummy_", _), T)) = dummy_pattern T
 | 
| 16035 | 1131  | 
| show_dummy_patterns (t $ u) = show_dummy_patterns t $ show_dummy_patterns u  | 
1132  | 
| show_dummy_patterns (Abs (x, T, t)) = Abs (x, T, show_dummy_patterns t)  | 
|
1133  | 
| show_dummy_patterns a = a;  | 
|
1134  | 
||
| 13484 | 1135  | 
|
| 20100 | 1136  | 
(* display variables *)  | 
1137  | 
||
| 
14786
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
1138  | 
fun string_of_vname (x, i) =  | 
| 
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
1139  | 
let  | 
| 15986 | 1140  | 
val idx = string_of_int i;  | 
1141  | 
val dot =  | 
|
1142  | 
(case rev (Symbol.explode x) of  | 
|
| 
62529
 
8b7bdfc09f3b
clarified treatment of fragments of Isabelle symbols during bootstrap;
 
wenzelm 
parents: 
61655 
diff
changeset
 | 
1143  | 
_ :: "\<^sub>" :: _ => false  | 
| 15986 | 1144  | 
| c :: _ => Symbol.is_digit c  | 
1145  | 
| _ => true);  | 
|
| 
14786
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
1146  | 
in  | 
| 
38980
 
af73cf0dc31f
turned show_question_marks into proper configuration option;
 
wenzelm 
parents: 
35986 
diff
changeset
 | 
1147  | 
if dot then "?" ^ x ^ "." ^ idx  | 
| 
 
af73cf0dc31f
turned show_question_marks into proper configuration option;
 
wenzelm 
parents: 
35986 
diff
changeset
 | 
1148  | 
else if i <> 0 then "?" ^ x ^ idx  | 
| 
 
af73cf0dc31f
turned show_question_marks into proper configuration option;
 
wenzelm 
parents: 
35986 
diff
changeset
 | 
1149  | 
else "?" ^ x  | 
| 
14786
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
1150  | 
end;  | 
| 
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
1151  | 
|
| 
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
1152  | 
fun string_of_vname' (x, ~1) = x  | 
| 
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
1153  | 
| string_of_vname' xi = string_of_vname xi;  | 
| 
 
24a7bc97a27a
moved some sort ops to sorts.ML; added string_of_vname (from Syntax module);
 
wenzelm 
parents: 
14695 
diff
changeset
 | 
1154  | 
|
| 
1364
 
8ea1a962ad72
files now define a structure to allow SML/NJ to optimize the code
 
clasohm 
parents: 
1029 
diff
changeset
 | 
1155  | 
end;  | 
| 
 
8ea1a962ad72
files now define a structure to allow SML/NJ to optimize the code
 
clasohm 
parents: 
1029 
diff
changeset
 | 
1156  | 
|
| 40841 | 1157  | 
structure Basic_Term: BASIC_TERM = Term;  | 
1158  | 
open Basic_Term;  |