src/Pure/ex/Def.thy
author wenzelm
Thu, 18 May 2023 15:34:01 +0200
changeset 78071 61a1bf9eb0ce
parent 78064 4e865c45458b
child 78095 bc42c074e58f
permissions -rw-r--r--
clarified data: avoid pointless Morphism.transform;
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
74287
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
     1
(*  Title:      Pure/ex/Def.thy
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
     2
    Author:     Makarius
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
     3
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
     4
Primitive constant definition, without fact definition;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
     5
automatic expansion via Simplifier (simproc).
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
     6
*)
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
     7
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
     8
theory Def
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
     9
  imports Pure
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    10
  keywords "def" :: thy_defn
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    11
begin
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    12
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    13
ML \<open>
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    14
signature DEF =
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    15
sig
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    16
  val get_def: Proof.context -> cterm -> thm option
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    17
  val def: (binding * typ option * mixfix) option ->
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    18
    (binding * typ option * mixfix) list -> term -> local_theory -> term * local_theory
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    19
  val def_cmd: (binding * string option * mixfix) option ->
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    20
    (binding * string option * mixfix) list -> string -> local_theory -> term * local_theory
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    21
end;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    22
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    23
structure Def: DEF =
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    24
struct
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    25
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    26
(* context data *)
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    27
78071
61a1bf9eb0ce clarified data: avoid pointless Morphism.transform;
wenzelm
parents: 78064
diff changeset
    28
type def = {lhs: term, eq: thm};
74287
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    29
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    30
val eq_def : def * def -> bool = op aconv o apply2 #lhs;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    31
78071
61a1bf9eb0ce clarified data: avoid pointless Morphism.transform;
wenzelm
parents: 78064
diff changeset
    32
fun transform_def phi ({lhs, eq}: def) =
61a1bf9eb0ce clarified data: avoid pointless Morphism.transform;
wenzelm
parents: 78064
diff changeset
    33
  {lhs = Morphism.term phi lhs, eq = Morphism.thm phi eq};
74287
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    34
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    35
structure Data = Generic_Data
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    36
(
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    37
  type T = def Item_Net.T;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    38
  val empty : T = Item_Net.init eq_def (single o #lhs);
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    39
  val merge = Item_Net.merge;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    40
);
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    41
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    42
fun declare_def lhs eq lthy =
78071
61a1bf9eb0ce clarified data: avoid pointless Morphism.transform;
wenzelm
parents: 78064
diff changeset
    43
  let val def0: def = {lhs = lhs, eq = Thm.trim_context eq} in
74287
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    44
    lthy |> Local_Theory.declaration {syntax = false, pervasive = true}
78049
d7395ef81292 proper transfer / trim_context;
wenzelm
parents: 74561
diff changeset
    45
      (fn phi => fn context =>
78064
4e865c45458b clarified transfer / trim_context on persistent Token.source (e.g. attribute expressions): actually set/reset implicit context;
wenzelm
parents: 78049
diff changeset
    46
        let val psi = Morphism.set_trim_context'' context phi
78071
61a1bf9eb0ce clarified data: avoid pointless Morphism.transform;
wenzelm
parents: 78064
diff changeset
    47
        in (Data.map o Item_Net.update) (transform_def psi def0) context end)
74287
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    48
  end;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    49
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    50
fun get_def ctxt ct =
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    51
  let
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    52
    val thy = Proof_Context.theory_of ctxt;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    53
    val data = Data.get (Context.Proof ctxt);
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    54
    val t = Thm.term_of ct;
78071
61a1bf9eb0ce clarified data: avoid pointless Morphism.transform;
wenzelm
parents: 78064
diff changeset
    55
    fun match_def {lhs, eq} =
74287
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    56
      if Pattern.matches thy (lhs, t) then
78071
61a1bf9eb0ce clarified data: avoid pointless Morphism.transform;
wenzelm
parents: 78064
diff changeset
    57
        let val inst = Thm.match (Thm.cterm_of ctxt lhs, ct)
61a1bf9eb0ce clarified data: avoid pointless Morphism.transform;
wenzelm
parents: 78064
diff changeset
    58
        in SOME (Thm.instantiate inst (Thm.transfer thy eq)) end
74287
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    59
      else NONE;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    60
  in Item_Net.retrieve_matching data t |> get_first match_def end;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    61
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    62
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    63
(* simproc setup *)
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    64
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    65
val _ =
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    66
  (Theory.setup o Named_Target.theory_map)
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    67
    (Simplifier.define_simproc \<^binding>\<open>expand_def\<close>
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    68
      {lhss = [Free ("x", TFree ("'a", []))], proc = K get_def});
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    69
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    70
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    71
(* Isar command *)
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    72
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    73
fun gen_def prep_spec raw_var raw_params raw_spec lthy =
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    74
  let
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    75
    val ((vars, xs, get_pos, spec), _) = lthy
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    76
      |> prep_spec (the_list raw_var) raw_params [] raw_spec;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    77
    val (((x, _), rhs), prove) = Local_Defs.derived_def lthy get_pos {conditional = false} spec;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    78
    val _ = Name.reject_internal (x, []);
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    79
    val (b, mx) =
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    80
      (case (vars, xs) of
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    81
        ([], []) => (Binding.make (x, (case get_pos x of [] => Position.none | p :: _ => p)), NoSyn)
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    82
      | ([(b, _, mx)], [y]) =>
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    83
          if x = y then (b, mx)
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    84
          else
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    85
            error ("Head of definition " ^ quote x ^ " differs from declaration " ^ quote y ^
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    86
              Position.here (Binding.pos_of b)));
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    87
    val ((lhs, (_, eq)), lthy') = lthy
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    88
      |> Local_Theory.define_internal ((b, mx), (Binding.empty_atts, rhs));
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    89
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    90
    (*sanity check for original specification*)
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    91
    val _: thm = prove lthy' eq;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    92
  in (lhs, declare_def lhs eq lthy') end;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    93
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    94
val def = gen_def Specification.check_spec_open;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    95
val def_cmd = gen_def Specification.read_spec_open;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    96
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    97
val _ =
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    98
  Outer_Syntax.local_theory \<^command_keyword>\<open>def\<close>
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
    99
    "primitive constant definition, without fact definition"
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
   100
    (Scan.option Parse_Spec.constdecl -- Parse.prop -- Parse.for_fixes
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
   101
      >> (fn ((decl, spec), params) => #2 o def_cmd decl params spec));
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
   102
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
   103
end;
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
   104
\<close>
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
   105
f79dfc7656ae miscellaneous examples and experiments for Isabelle/Pure;
wenzelm
parents:
diff changeset
   106
end