28 val size_neqN = "size_neq"; |
28 val size_neqN = "size_neq"; |
29 |
29 |
30 val nitpicksimp_attrs = @{attributes [nitpick_simp]}; |
30 val nitpicksimp_attrs = @{attributes [nitpick_simp]}; |
31 val simp_attrs = @{attributes [simp]}; |
31 val simp_attrs = @{attributes [simp]}; |
32 |
32 |
|
33 fun mk_plus_nat (t1, t2) = Const (@{const_name Groups.plus}, |
|
34 HOLogic.natT --> HOLogic.natT --> HOLogic.natT) $ t1 $ t2; |
|
35 |
|
36 fun mk_to_natT T = T --> HOLogic.natT; |
|
37 |
|
38 fun mk_abs_zero_nat T = Term.absdummy T HOLogic.zero; |
|
39 |
|
40 fun mk_pointful ctxt thm = unfold_thms ctxt [o_apply] (thm RS fun_cong); |
|
41 |
|
42 fun mk_unabs_def_unused_0 n = |
|
43 funpow n (fn thm => thm RS @{thm fun_cong_unused_0} handle THM _ => thm RS fun_cong); |
|
44 |
33 structure Data = Generic_Data |
45 structure Data = Generic_Data |
34 ( |
46 ( |
35 type T = (string * (thm list * thm list)) Symtab.table; |
47 type T = (string * (thm list * thm list)) Symtab.table; |
36 val empty = Symtab.empty; |
48 val empty = Symtab.empty; |
37 val extend = I |
49 val extend = I |
38 fun merge data = Symtab.merge (K true) data; |
50 fun merge data = Symtab.merge (K true) data; |
39 ); |
51 ); |
40 |
52 |
41 fun register_size T_name size_name size_simps size_gen_o_maps = |
53 fun check_size_type thy T_name size_name = |
42 Context.proof_map (Data.map (Symtab.update (T_name, (size_name, (size_simps, size_gen_o_maps))))); |
54 let |
43 |
55 val n = Sign.arity_number thy T_name; |
44 fun register_size_global T_name size_name size_simps size_gen_o_maps = |
56 val As = map (fn s => TFree (s, @{sort type})) (Name.invent Name.context Name.aT n); |
45 Context.theory_map |
57 val T = Type (T_name, As); |
46 (Data.map (Symtab.update (T_name, (size_name, (size_simps, size_gen_o_maps))))); |
58 val size_T = map mk_to_natT As ---> mk_to_natT T; |
|
59 val size_const = Const (size_name, size_T); |
|
60 in |
|
61 can (Thm.global_cterm_of thy) size_const orelse |
|
62 error ("Constant " ^ quote size_name ^ " registered as size function for " ^ quote T_name ^ |
|
63 " must have type\n" ^ quote (Syntax.string_of_typ_global thy size_T)) |
|
64 end; |
|
65 |
|
66 fun register_size T_name size_name size_simps size_gen_o_maps lthy = |
|
67 (check_size_type (Proof_Context.theory_of lthy) T_name size_name; |
|
68 Context.proof_map (Data.map (Symtab.update (T_name, (size_name, (size_simps, size_gen_o_maps))))) |
|
69 lthy); |
|
70 |
|
71 fun register_size_global T_name size_name size_simps size_gen_o_maps thy = |
|
72 (check_size_type thy T_name size_name; |
|
73 Context.theory_map (Data.map (Symtab.update (T_name, (size_name, (size_simps, |
|
74 size_gen_o_maps))))) thy); |
47 |
75 |
48 val size_of = Symtab.lookup o Data.get o Context.Proof; |
76 val size_of = Symtab.lookup o Data.get o Context.Proof; |
49 val size_of_global = Symtab.lookup o Data.get o Context.Theory; |
77 val size_of_global = Symtab.lookup o Data.get o Context.Theory; |
50 |
|
51 fun mk_plus_nat (t1, t2) = Const (@{const_name Groups.plus}, |
|
52 HOLogic.natT --> HOLogic.natT --> HOLogic.natT) $ t1 $ t2; |
|
53 |
|
54 fun mk_to_natT T = T --> HOLogic.natT; |
|
55 |
|
56 fun mk_abs_zero_nat T = Term.absdummy T HOLogic.zero; |
|
57 |
|
58 fun mk_pointful ctxt thm = unfold_thms ctxt [o_apply] (thm RS fun_cong); |
|
59 |
|
60 fun mk_unabs_def_unused_0 n = |
|
61 funpow n (fn thm => thm RS @{thm fun_cong_unused_0} handle THM _ => thm RS fun_cong); |
|
62 |
78 |
63 val size_gen_o_map_simps = @{thms inj_on_id snd_comp_apfst[unfolded apfst_def]}; |
79 val size_gen_o_map_simps = @{thms inj_on_id snd_comp_apfst[unfolded apfst_def]}; |
64 |
80 |
65 fun mk_size_gen_o_map_tac ctxt size_def rec_o_map inj_maps size_maps = |
81 fun mk_size_gen_o_map_tac ctxt size_def rec_o_map inj_maps size_maps = |
66 unfold_thms_tac ctxt [size_def] THEN |
82 unfold_thms_tac ctxt [size_def] THEN |
123 else if exists (exists_subtype_in (As @ Cs)) Ts then |
139 else if exists (exists_subtype_in (As @ Cs)) Ts then |
124 (case Symtab.lookup data s of |
140 (case Symtab.lookup data s of |
125 SOME (size_name, (_, size_gen_o_maps)) => |
141 SOME (size_name, (_, size_gen_o_maps)) => |
126 let |
142 let |
127 val (args, size_gen_o_mapss') = fold_map mk_size_of_typ Ts []; |
143 val (args, size_gen_o_mapss') = fold_map mk_size_of_typ Ts []; |
128 val size_const = Const (size_name, map fastype_of args ---> mk_to_natT T); |
144 val size_T = map fastype_of args ---> mk_to_natT T; |
|
145 val size_const = Const (size_name, size_T); |
129 in |
146 in |
130 append (size_gen_o_maps :: size_gen_o_mapss') |
147 append (size_gen_o_maps :: size_gen_o_mapss') |
131 #> pair (Term.list_comb (size_const, args)) |
148 #> pair (Term.list_comb (size_const, args)) |
132 end |
149 end |
133 | _ => pair (mk_abs_zero_nat T)) |
150 | _ => pair (mk_abs_zero_nat T)) |