| author | wenzelm | 
| Fri, 04 Apr 2025 16:35:05 +0200 | |
| changeset 82432 | 314d6b215f90 | 
| parent 82008 | 7301923ad1e9 | 
| permissions | -rw-r--r-- | 
| 81989 
96afb0707532
move theory "HOL-Library.Adhoc_Overloading" to Pure;
 wenzelm parents: 
81253diff
changeset | 1 | (* Title: Pure/Tools/adhoc_overloading.ML | 
| 
96afb0707532
move theory "HOL-Library.Adhoc_Overloading" to Pure;
 wenzelm parents: 
81253diff
changeset | 2 | Author: Alexander Krauss, TU Muenchen | 
| 53538 | 3 | Author: Christian Sternagel, University of Innsbruck | 
| 37789 | 4 | |
| 52893 | 5 | Adhoc overloading of constants based on their types. | 
| 37789 | 6 | *) | 
| 7 | ||
| 8 | signature ADHOC_OVERLOADING = | |
| 9 | sig | |
| 81989 
96afb0707532
move theory "HOL-Library.Adhoc_Overloading" to Pure;
 wenzelm parents: 
81253diff
changeset | 10 | val show_variants: bool Config.T | 
| 81992 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 11 | val adhoc_overloading: bool -> (string * term list) list -> local_theory -> local_theory | 
| 81989 
96afb0707532
move theory "HOL-Library.Adhoc_Overloading" to Pure;
 wenzelm parents: 
81253diff
changeset | 12 | val adhoc_overloading_cmd: bool -> (string * string list) list -> local_theory -> local_theory | 
| 37789 | 13 | end | 
| 14 | ||
| 15 | structure Adhoc_Overloading: ADHOC_OVERLOADING = | |
| 16 | struct | |
| 17 | ||
| 69593 | 18 | val show_variants = Attrib.setup_config_bool \<^binding>\<open>show_variants\<close> (K false); | 
| 37789 | 19 | |
| 53538 | 20 | |
| 37789 | 21 | (* errors *) | 
| 22 | ||
| 53008 
128bec4e3fca
indicate error-functions more prominently (by name prefix instead of suffix);
 Christian Sternagel parents: 
53007diff
changeset | 23 | fun err_duplicate_variant oconst = | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 24 |   error ("Duplicate variant of " ^ quote oconst);
 | 
| 37789 | 25 | |
| 53008 
128bec4e3fca
indicate error-functions more prominently (by name prefix instead of suffix);
 Christian Sternagel parents: 
53007diff
changeset | 26 | fun err_not_a_variant oconst = | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 27 |   error ("Not a variant of " ^  quote oconst);
 | 
| 37789 | 28 | |
| 53008 
128bec4e3fca
indicate error-functions more prominently (by name prefix instead of suffix);
 Christian Sternagel parents: 
53007diff
changeset | 29 | fun err_not_overloaded oconst = | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 30 |   error ("Constant " ^ quote oconst ^ " is not declared as overloaded");
 | 
| 37789 | 31 | |
| 53540 
7903fe2c271b
prefer explicit type constraint (again, see also Type.appl_error);
 wenzelm parents: 
53538diff
changeset | 32 | fun err_unresolved_overloading ctxt0 (c, T) t instances = | 
| 
7903fe2c271b
prefer explicit type constraint (again, see also Type.appl_error);
 wenzelm parents: 
53538diff
changeset | 33 | let | 
| 
7903fe2c271b
prefer explicit type constraint (again, see also Type.appl_error);
 wenzelm parents: 
53538diff
changeset | 34 | val ctxt = Config.put show_variants true ctxt0 | 
| 
7903fe2c271b
prefer explicit type constraint (again, see also Type.appl_error);
 wenzelm parents: 
53538diff
changeset | 35 | val const_space = Proof_Context.const_space ctxt | 
| 
7903fe2c271b
prefer explicit type constraint (again, see also Type.appl_error);
 wenzelm parents: 
53538diff
changeset | 36 | val prt_const = | 
| 
7903fe2c271b
prefer explicit type constraint (again, see also Type.appl_error);
 wenzelm parents: 
53538diff
changeset | 37 | Pretty.block [Name_Space.pretty ctxt const_space c, Pretty.str " ::", Pretty.brk 1, | 
| 
7903fe2c271b
prefer explicit type constraint (again, see also Type.appl_error);
 wenzelm parents: 
53538diff
changeset | 38 | Pretty.quote (Syntax.pretty_typ ctxt T)] | 
| 52688 
1e13b2515e2b
show variants in error messages; more precise error messages (give witnesses for multiple instances)
 Christian Sternagel parents: 
52687diff
changeset | 39 | in | 
| 53537 | 40 | error (Pretty.string_of (Pretty.chunks [ | 
| 41 | Pretty.block [ | |
| 42 | Pretty.str "Unresolved adhoc overloading of constant", Pretty.brk 1, | |
| 53540 
7903fe2c271b
prefer explicit type constraint (again, see also Type.appl_error);
 wenzelm parents: 
53538diff
changeset | 43 | prt_const, Pretty.brk 1, Pretty.str "in term", Pretty.brk 1, | 
| 
7903fe2c271b
prefer explicit type constraint (again, see also Type.appl_error);
 wenzelm parents: 
53538diff
changeset | 44 | Pretty.block [Pretty.quote (Syntax.pretty_term ctxt t)]], | 
| 53537 | 45 | Pretty.block ( | 
| 46 | (if null instances then [Pretty.str "no instances"] | |
| 47 | else Pretty.fbreaks ( | |
| 48 | Pretty.str "multiple instances:" :: | |
| 53540 
7903fe2c271b
prefer explicit type constraint (again, see also Type.appl_error);
 wenzelm parents: 
53538diff
changeset | 49 | map (Pretty.mark Markup.item o Syntax.pretty_term ctxt) instances)))])) | 
| 52688 
1e13b2515e2b
show variants in error messages; more precise error messages (give witnesses for multiple instances)
 Christian Sternagel parents: 
52687diff
changeset | 50 | end; | 
| 37789 | 51 | |
| 53538 | 52 | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 53 | (* generic data *) | 
| 37789 | 54 | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 55 | fun variants_eq ((v1, T1), (v2, T2)) = | 
| 81991 | 56 | Term.aconv_untyped (v1, v2) andalso Type.raw_equiv (T1, T2); | 
| 37789 | 57 | |
| 82000 | 58 | structure Data = Generic_Data | 
| 37789 | 59 | ( | 
| 60 | type T = | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 61 |     {variants : (term * typ) list Symtab.table,
 | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 62 | oconsts : string Termtab.table}; | 
| 82003 | 63 |   val empty : T = {variants = Symtab.empty, oconsts = Termtab.empty};
 | 
| 37789 | 64 | |
| 41472 
f6ab14e61604
misc tuning and comments based on review of Theory_Data, Proof_Data, Generic_Data usage;
 wenzelm parents: 
37818diff
changeset | 65 | fun merge | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 66 |     ({variants = vtab1, oconsts = otab1},
 | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 67 |      {variants = vtab2, oconsts = otab2}) : T =
 | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 68 | let | 
| 82002 | 69 | fun join (oconst1, oconst2) = | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 70 | if oconst1 = oconst2 then oconst1 | 
| 53008 
128bec4e3fca
indicate error-functions more prominently (by name prefix instead of suffix);
 Christian Sternagel parents: 
53007diff
changeset | 71 | else err_duplicate_variant oconst1; | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 72 | in | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 73 |       {variants = Symtab.merge_list variants_eq (vtab1, vtab2),
 | 
| 82002 | 74 | oconsts = Termtab.join (K join) (otab1, otab2)} | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 75 | end; | 
| 37789 | 76 | ); | 
| 77 | ||
| 82003 | 78 | fun map_data f = | 
| 79 |   Data.map (fn {variants, oconsts} =>
 | |
| 80 | let val (variants', oconsts') = f (variants, oconsts) | |
| 81 |     in {variants = variants', oconsts = oconsts'} end);
 | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 82 | |
| 82005 | 83 | val no_variants = Symtab.is_empty o #variants o Data.get; | 
| 84 | val has_variants = Symtab.defined o #variants o Data.get; | |
| 82001 
ae454f0c4f4c
clarified signature with minor performance tuning: avoid Context.proof_of with its Proof_Context.init_global;
 wenzelm parents: 
82000diff
changeset | 85 | val get_variants = Symtab.lookup o #variants o Data.get; | 
| 
ae454f0c4f4c
clarified signature with minor performance tuning: avoid Context.proof_of with its Proof_Context.init_global;
 wenzelm parents: 
82000diff
changeset | 86 | val get_overloaded = Termtab.lookup o #oconsts o Data.get; | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 87 | |
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 88 | fun generic_add_overloaded oconst context = | 
| 82005 | 89 | if has_variants context oconst then context | 
| 82003 | 90 | else (map_data o apfst) (Symtab.update (oconst, [])) context; | 
| 37789 | 91 | |
| 81992 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 92 | (*If the list of variants is empty at the end of "generic_remove_variant", then | 
| 82000 | 93 | "generic_remove_overloaded" is called implicitly.*) | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 94 | fun generic_remove_overloaded oconst context = | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 95 | let | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 96 | fun remove_oconst_and_variants context oconst = | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 97 | let | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 98 | val remove_variants = | 
| 82001 
ae454f0c4f4c
clarified signature with minor performance tuning: avoid Context.proof_of with its Proof_Context.init_global;
 wenzelm parents: 
82000diff
changeset | 99 | (case get_variants context oconst of | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 100 | NONE => I | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 101 | | SOME vs => fold (Termtab.remove (op =) o rpair oconst o fst) vs); | 
| 82003 | 102 | in | 
| 103 | context |> map_data (fn (variants, oconsts) => | |
| 104 | (Symtab.delete_safe oconst variants, remove_variants oconsts)) | |
| 105 | end; | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 106 | in | 
| 82005 | 107 | if has_variants context oconst then remove_oconst_and_variants context oconst | 
| 53008 
128bec4e3fca
indicate error-functions more prominently (by name prefix instead of suffix);
 Christian Sternagel parents: 
53007diff
changeset | 108 | else err_not_overloaded oconst | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 109 | end; | 
| 37789 | 110 | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 111 | local | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 112 | fun generic_variant add oconst t context = | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 113 | let | 
| 82005 | 114 | val _ = if has_variants context oconst then () else err_not_overloaded oconst; | 
| 82008 | 115 | val T = fastype_of t; | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 116 | val t' = Term.map_types (K dummyT) t; | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 117 | in | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 118 | if add then | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 119 | let | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 120 | val _ = | 
| 82001 
ae454f0c4f4c
clarified signature with minor performance tuning: avoid Context.proof_of with its Proof_Context.init_global;
 wenzelm parents: 
82000diff
changeset | 121 | (case get_overloaded context t' of | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 122 | NONE => () | 
| 53008 
128bec4e3fca
indicate error-functions more prominently (by name prefix instead of suffix);
 Christian Sternagel parents: 
53007diff
changeset | 123 | | SOME oconst' => err_duplicate_variant oconst'); | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 124 | in | 
| 82003 | 125 | context |> map_data (fn (variants, oconsts) => | 
| 126 | (Symtab.cons_list (oconst, (t', T)) variants, Termtab.update (t', oconst) oconsts)) | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 127 | end | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 128 | else | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 129 | let | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 130 | val _ = | 
| 82001 
ae454f0c4f4c
clarified signature with minor performance tuning: avoid Context.proof_of with its Proof_Context.init_global;
 wenzelm parents: 
82000diff
changeset | 131 | if member variants_eq (the (get_variants context oconst)) (t', T) then () | 
| 53008 
128bec4e3fca
indicate error-functions more prominently (by name prefix instead of suffix);
 Christian Sternagel parents: 
53007diff
changeset | 132 | else err_not_a_variant oconst; | 
| 82003 | 133 | val context' = | 
| 134 | context |> map_data (fn (variants, oconsts) => | |
| 135 | (Symtab.map_entry oconst (remove1 variants_eq (t', T)) variants, | |
| 136 | Termtab.delete_safe t' oconsts)); | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 137 | in | 
| 82003 | 138 | (case get_variants context' oconst of | 
| 139 | SOME [] => generic_remove_overloaded oconst context' | |
| 140 | | _ => context') | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 141 | end | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 142 | end; | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 143 | in | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 144 | val generic_add_variant = generic_variant true; | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 145 | val generic_remove_variant = generic_variant false; | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 146 | end; | 
| 37789 | 147 | |
| 53538 | 148 | |
| 37789 | 149 | (* check / uncheck *) | 
| 150 | ||
| 82002 | 151 | local | 
| 152 | ||
| 153 | fun unifiable_types ctxt (T1, T2) = | |
| 37789 | 154 | let | 
| 82002 | 155 | val thy = Proof_Context.theory_of ctxt; | 
| 37789 | 156 | val maxidx1 = Term.maxidx_of_typ T1; | 
| 157 | val T2' = Logic.incr_tvar (maxidx1 + 1) T2; | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 158 | val maxidx2 = Term.maxidx_typ T2' maxidx1; | 
| 53004 | 159 | in can (Sign.typ_unify thy (T1, T2')) (Vartab.empty, maxidx2) end; | 
| 37789 | 160 | |
| 53006 
83d9984ee639
avoid misleading "instances" in function name;
 Christian Sternagel parents: 
53005diff
changeset | 161 | fun get_candidates ctxt (c, T) = | 
| 82001 
ae454f0c4f4c
clarified signature with minor performance tuning: avoid Context.proof_of with its Proof_Context.init_global;
 wenzelm parents: 
82000diff
changeset | 162 | get_variants (Context.Proof ctxt) c | 
| 53007 | 163 | |> Option.map (map_filter (fn (t, T') => | 
| 82002 | 164 | if unifiable_types ctxt (T, T') | 
| 80127 
39f9084a9668
make adhoc_overloading respect type constraints
 Kevin Kappelmann <kevin.kappelmann@tum.de> parents: 
78095diff
changeset | 165 | (*keep the type constraint for the type-inference check phase*) | 
| 
39f9084a9668
make adhoc_overloading respect type constraints
 Kevin Kappelmann <kevin.kappelmann@tum.de> parents: 
78095diff
changeset | 166 | then SOME (Type.constraint T t) | 
| 53007 | 167 | else NONE)); | 
| 52687 | 168 | |
| 82002 | 169 | val the_candidates = the oo get_candidates; | 
| 170 | ||
| 82007 | 171 | fun insert_variants_same ctxt t : term Same.operation = | 
| 172 | (fn Const const => | |
| 173 | (case get_candidates ctxt const of | |
| 174 | SOME [] => err_unresolved_overloading ctxt const t [] | |
| 53007 | 175 | | SOME [variant] => variant | 
| 82007 | 176 | | _ => raise Same.SAME) | 
| 177 | | _ => raise Same.SAME); | |
| 37789 | 178 | |
| 54004 | 179 | fun insert_overloaded ctxt = | 
| 180 | let | |
| 82002 | 181 | val thy = Proof_Context.theory_of ctxt; | 
| 54004 | 182 | fun proc t = | 
| 183 | Term.map_types (K dummyT) t | |
| 82001 
ae454f0c4f4c
clarified signature with minor performance tuning: avoid Context.proof_of with its Proof_Context.init_global;
 wenzelm parents: 
82000diff
changeset | 184 | |> get_overloaded (Context.Proof ctxt) | 
| 54004 | 185 | |> Option.map (Const o rpair (Term.type_of t)); | 
| 186 | in | |
| 82002 | 187 | Pattern.rewrite_term_yoyo thy [] [proc] | 
| 54004 | 188 | end; | 
| 53007 | 189 | |
| 82008 | 190 | fun overloaded_term_consts ctxt = | 
| 82004 
aaa7e388265a
minor performance tuning: avoid somewhat indirect filter / add_consts;
 wenzelm parents: 
82003diff
changeset | 191 | let | 
| 
aaa7e388265a
minor performance tuning: avoid somewhat indirect filter / add_consts;
 wenzelm parents: 
82003diff
changeset | 192 | val context = Context.Proof ctxt; | 
| 82005 | 193 | val overloaded = has_variants context; | 
| 82008 | 194 | val add = fn Const (c, T) => if overloaded c then insert (op =) (c, T) else I | _ => I; | 
| 195 | in fn t => if no_variants context then [] else fold_aterms add t [] end; | |
| 82004 
aaa7e388265a
minor performance tuning: avoid somewhat indirect filter / add_consts;
 wenzelm parents: 
82003diff
changeset | 196 | |
| 82002 | 197 | in | 
| 198 | ||
| 53007 | 199 | fun check ctxt = | 
| 82005 | 200 | if no_variants (Context.Proof ctxt) then I | 
| 82008 | 201 | else map (fn t => t |> Term.map_aterms (insert_variants_same ctxt t)); | 
| 53007 | 202 | |
| 54468 
f6ffe53387ef
reintroduced e2d08b9c9047, lost in 54e290da6da8 + e13b0c88c798
 traytel parents: 
54004diff
changeset | 203 | fun uncheck ctxt ts = | 
| 82006 | 204 | if Config.get ctxt show_variants orelse exists (not o can Term.type_of) ts then ts | 
| 54468 
f6ffe53387ef
reintroduced e2d08b9c9047, lost in 54e290da6da8 + e13b0c88c798
 traytel parents: 
54004diff
changeset | 205 | else map (insert_overloaded ctxt) ts; | 
| 53007 | 206 | |
| 207 | fun reject_unresolved ctxt = | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 208 | let | 
| 37789 | 209 | fun check_unresolved t = | 
| 82008 | 210 | (case overloaded_term_consts ctxt t of | 
| 53007 | 211 | [] => t | 
| 82004 
aaa7e388265a
minor performance tuning: avoid somewhat indirect filter / add_consts;
 wenzelm parents: 
82003diff
changeset | 212 | | const :: _ => err_unresolved_overloading ctxt const t (the_candidates ctxt const)); | 
| 53007 | 213 | in map check_unresolved end; | 
| 37789 | 214 | |
| 82002 | 215 | end; | 
| 216 | ||
| 53538 | 217 | |
| 37789 | 218 | (* setup *) | 
| 219 | ||
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 220 | val _ = Context.>> | 
| 53007 | 221 | (Syntax_Phases.term_check 0 "adhoc_overloading" check | 
| 222 | #> Syntax_Phases.term_check 1 "adhoc_overloading_unresolved_check" reject_unresolved | |
| 223 | #> Syntax_Phases.term_uncheck 0 "adhoc_overloading" uncheck); | |
| 37789 | 224 | |
| 53538 | 225 | |
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 226 | (* commands *) | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 227 | |
| 81992 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 228 | local | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 229 | |
| 81994 
5e50a2b52809
support for "no" polarity of 'adhoc_overloading' vs. 'no_adhoc_overloading';
 wenzelm parents: 
81992diff
changeset | 230 | fun generic_adhoc_overloading add args context = | 
| 
5e50a2b52809
support for "no" polarity of 'adhoc_overloading' vs. 'no_adhoc_overloading';
 wenzelm parents: 
81992diff
changeset | 231 | if Syntax.effective_polarity_generic context add then | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 232 | fold (fn (oconst, ts) => | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 233 | generic_add_overloaded oconst | 
| 81994 
5e50a2b52809
support for "no" polarity of 'adhoc_overloading' vs. 'no_adhoc_overloading';
 wenzelm parents: 
81992diff
changeset | 234 | #> fold (generic_add_variant oconst) ts) args context | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 235 | else | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 236 | fold (fn (oconst, ts) => | 
| 81994 
5e50a2b52809
support for "no" polarity of 'adhoc_overloading' vs. 'no_adhoc_overloading';
 wenzelm parents: 
81992diff
changeset | 237 | fold (generic_remove_variant oconst) ts) args context; | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 238 | |
| 81992 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 239 | fun gen_adhoc_overloading prep_arg add raw_args lthy = | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 240 | let | 
| 81992 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 241 | val args = map (prep_arg lthy) raw_args; | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 242 | in | 
| 81992 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 243 |     lthy |> Local_Theory.declaration {syntax = true, pervasive = false, pos = Position.thread_data ()}
 | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 244 | (fn phi => | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 245 | let val args' = args | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 246 | |> map (apsnd (map_filter (fn t => | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 247 | let val t' = Morphism.term phi t; | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 248 | in if Term.aconv_untyped (t, t') then SOME t' else NONE end))); | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 249 | in generic_adhoc_overloading add args' end) | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 250 | end; | 
| 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 251 | |
| 81992 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 252 | fun cert_const_name ctxt c = | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 253 | (Consts.the_const_type (Proof_Context.consts_of ctxt) c; c); | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 254 | |
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 255 | fun read_const_name ctxt = | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 256 |   dest_Const_name o Proof_Context.read_const {proper = true, strict = true} ctxt;
 | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 257 | |
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 258 | fun cert_term ctxt = Proof_Context.cert_term ctxt #> singleton (Variable.polymorphic ctxt); | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 259 | fun read_term ctxt = Syntax.read_term ctxt #> singleton (Variable.polymorphic ctxt); | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 260 | |
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 261 | in | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 262 | |
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 263 | val adhoc_overloading = | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 264 | gen_adhoc_overloading (fn ctxt => fn (c, ts) => (cert_const_name ctxt c, map (cert_term ctxt) ts)); | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 265 | |
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 266 | val adhoc_overloading_cmd = | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 267 | gen_adhoc_overloading (fn ctxt => fn (c, ts) => (read_const_name ctxt c, map (read_term ctxt) ts)); | 
| 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 268 | |
| 45422 | 269 | end; | 
| 52622 
e0ff1625e96d
localized and modernized adhoc-overloading (patch by Christian Sternagel);
 wenzelm parents: 
50768diff
changeset | 270 | |
| 81992 
be1328008ee2
clarified signature: proper ML interface to main command, without exposing too many internals;
 wenzelm parents: 
81991diff
changeset | 271 | end; |