src/HOL/Tools/inductive_set.ML
changeset 50774 ac53370dfae1
parent 49324 4f28543ae7fa
child 51717 9e7d1c139569
equal deleted inserted replaced
50773:205d12333fdc 50774:ac53370dfae1
   154 (* S {(x, y). p x y} = {(x, y). P p x y}                   *)
   154 (* S {(x, y). p x y} = {(x, y). P p x y}                   *)
   155 (*                                                         *)
   155 (*                                                         *)
   156 (* where s and p are parameters                            *)
   156 (* where s and p are parameters                            *)
   157 (***********************************************************)
   157 (***********************************************************)
   158 
   158 
   159 structure PredSetConvData = Generic_Data
   159 structure Data = Generic_Data
   160 (
   160 (
   161   type T =
   161   type T =
   162     {(* rules for converting predicates to sets *)
   162     {(* rules for converting predicates to sets *)
   163      to_set_simps: thm list,
   163      to_set_simps: thm list,
   164      (* rules for converting sets to predicates *)
   164      (* rules for converting sets to predicates *)
   267   end;
   267   end;
   268 
   268 
   269 
   269 
   270 (**** declare rules for converting predicates to sets ****)
   270 (**** declare rules for converting predicates to sets ****)
   271 
   271 
   272 fun add ctxt thm (tab as {to_set_simps, to_pred_simps, set_arities, pred_arities}) =
   272 exception Malformed of string;
   273   case prop_of thm of
   273 
       
   274 fun add context thm (tab as {to_set_simps, to_pred_simps, set_arities, pred_arities}) =
       
   275   (case prop_of thm of
   274     Const (@{const_name Trueprop}, _) $ (Const (@{const_name HOL.eq}, Type (_, [T, _])) $ lhs $ rhs) =>
   276     Const (@{const_name Trueprop}, _) $ (Const (@{const_name HOL.eq}, Type (_, [T, _])) $ lhs $ rhs) =>
   275       (case body_type T of
   277       (case body_type T of
   276          @{typ bool} =>
   278          @{typ bool} =>
   277            let
   279            let
   278              val thy = Context.theory_of ctxt;
   280              val thy = Context.theory_of context;
   279              fun factors_of t fs = case strip_abs_body t of
   281              fun factors_of t fs = case strip_abs_body t of
   280                  Const (@{const_name Set.member}, _) $ u $ S =>
   282                  Const (@{const_name Set.member}, _) $ u $ S =>
   281                    if is_Free S orelse is_Var S then
   283                    if is_Free S orelse is_Var S then
   282                      let val ps = HOLogic.flat_tuple_paths u
   284                      let val ps = HOLogic.flat_tuple_paths u
   283                      in (SOME ps, (S, ps) :: fs) end
   285                      in (SOME ps, (S, ps) :: fs) end
   287              val (pfs, fs) = fold_map factors_of ts [];
   289              val (pfs, fs) = fold_map factors_of ts [];
   288              val ((h', ts'), fs') = (case rhs of
   290              val ((h', ts'), fs') = (case rhs of
   289                  Abs _ => (case strip_abs_body rhs of
   291                  Abs _ => (case strip_abs_body rhs of
   290                      Const (@{const_name Set.member}, _) $ u $ S =>
   292                      Const (@{const_name Set.member}, _) $ u $ S =>
   291                        (strip_comb S, SOME (HOLogic.flat_tuple_paths u))
   293                        (strip_comb S, SOME (HOLogic.flat_tuple_paths u))
   292                    | _ => error "member symbol on right-hand side expected")
   294                    | _ => raise Malformed "member symbol on right-hand side expected")
   293                | _ => (strip_comb rhs, NONE))
   295                | _ => (strip_comb rhs, NONE))
   294            in
   296            in
   295              case (name_type_of h, name_type_of h') of
   297              case (name_type_of h, name_type_of h') of
   296                (SOME (s, T), SOME (s', T')) =>
   298                (SOME (s, T), SOME (s', T')) =>
   297                  if exists (fn (U, _) =>
   299                  if exists (fn (U, _) =>
   306                       mk_to_pred_eq h fs fs' T' thm :: to_pred_simps,
   308                       mk_to_pred_eq h fs fs' T' thm :: to_pred_simps,
   307                     set_arities = Symtab.insert_list op = (s',
   309                     set_arities = Symtab.insert_list op = (s',
   308                       (T', (map (AList.lookup op = fs) ts', fs'))) set_arities,
   310                       (T', (map (AList.lookup op = fs) ts', fs'))) set_arities,
   309                     pred_arities = Symtab.insert_list op = (s,
   311                     pred_arities = Symtab.insert_list op = (s,
   310                       (T, (pfs, fs'))) pred_arities}
   312                       (T, (pfs, fs'))) pred_arities}
   311              | _ => error "set / predicate constant expected"
   313              | _ => raise Malformed "set / predicate constant expected"
   312            end
   314            end
   313        | _ => error "equation between predicates expected")
   315        | _ => raise Malformed "equation between predicates expected")
   314   | _ => error "equation expected";
   316   | _ => raise Malformed "equation expected")
       
   317   handle Malformed msg =>
       
   318     (warning ("Ignoring malformed set / predicate conversion rule: " ^ msg ^
       
   319       "\n" ^ Display.string_of_thm (Context.proof_of context) thm); tab);
   315 
   320 
   316 val pred_set_conv_att = Thm.declaration_attribute
   321 val pred_set_conv_att = Thm.declaration_attribute
   317   (fn thm => fn ctxt => PredSetConvData.map (add ctxt thm) ctxt);
   322   (fn thm => fn ctxt => Data.map (add ctxt thm) ctxt);
   318 
   323 
   319 
   324 
   320 (**** convert theorem in set notation to predicate notation ****)
   325 (**** convert theorem in set notation to predicate notation ****)
   321 
   326 
   322 fun is_pred tab t =
   327 fun is_pred tab t =
   338 
   343 
   339 fun to_pred thms ctxt thm =
   344 fun to_pred thms ctxt thm =
   340   let
   345   let
   341     val thy = Context.theory_of ctxt;
   346     val thy = Context.theory_of ctxt;
   342     val {to_pred_simps, set_arities, pred_arities, ...} =
   347     val {to_pred_simps, set_arities, pred_arities, ...} =
   343       fold (add ctxt) thms (PredSetConvData.get ctxt);
   348       fold (add ctxt) thms (Data.get ctxt);
   344     val fs = filter (is_Var o fst)
   349     val fs = filter (is_Var o fst)
   345       (infer_arities thy set_arities (NONE, prop_of thm) []);
   350       (infer_arities thy set_arities (NONE, prop_of thm) []);
   346     (* instantiate each set parameter with {(x, y). p x y} *)
   351     (* instantiate each set parameter with {(x, y). p x y} *)
   347     val insts = mk_to_pred_inst thy fs
   352     val insts = mk_to_pred_inst thy fs
   348   in
   353   in
   361 
   366 
   362 fun to_set thms ctxt thm =
   367 fun to_set thms ctxt thm =
   363   let
   368   let
   364     val thy = Context.theory_of ctxt;
   369     val thy = Context.theory_of ctxt;
   365     val {to_set_simps, pred_arities, ...} =
   370     val {to_set_simps, pred_arities, ...} =
   366       fold (add ctxt) thms (PredSetConvData.get ctxt);
   371       fold (add ctxt) thms (Data.get ctxt);
   367     val fs = filter (is_Var o fst)
   372     val fs = filter (is_Var o fst)
   368       (infer_arities thy pred_arities (NONE, prop_of thm) []);
   373       (infer_arities thy pred_arities (NONE, prop_of thm) []);
   369     (* instantiate each predicate parameter with %x y. (x, y) : s *)
   374     (* instantiate each predicate parameter with %x y. (x, y) : s *)
   370     val insts = map (fn (x, ps) =>
   375     val insts = map (fn (x, ps) =>
   371       let
   376       let
   395 (**** preprocessor for code generator ****)
   400 (**** preprocessor for code generator ****)
   396 
   401 
   397 fun codegen_preproc thy =
   402 fun codegen_preproc thy =
   398   let
   403   let
   399     val {to_pred_simps, set_arities, pred_arities, ...} =
   404     val {to_pred_simps, set_arities, pred_arities, ...} =
   400       PredSetConvData.get (Context.Theory thy);
   405       Data.get (Context.Theory thy);
   401     fun preproc thm =
   406     fun preproc thm =
   402       if exists_Const (fn (s, _) => case Symtab.lookup set_arities s of
   407       if exists_Const (fn (s, _) => case Symtab.lookup set_arities s of
   403           NONE => false
   408           NONE => false
   404         | SOME arities => exists (fn (_, (xs, _)) =>
   409         | SOME arities => exists (fn (_, (xs, _)) =>
   405             forall is_none xs) arities) (prop_of thm)
   410             forall is_none xs) arities) (prop_of thm)
   420     {quiet_mode, verbose, alt_name, coind, no_elim, no_ind, skip_mono}
   425     {quiet_mode, verbose, alt_name, coind, no_elim, no_ind, skip_mono}
   421     cs intros monos params cnames_syn lthy =
   426     cs intros monos params cnames_syn lthy =
   422   let
   427   let
   423     val thy = Proof_Context.theory_of lthy;
   428     val thy = Proof_Context.theory_of lthy;
   424     val {set_arities, pred_arities, to_pred_simps, ...} =
   429     val {set_arities, pred_arities, to_pred_simps, ...} =
   425       PredSetConvData.get (Context.Proof lthy);
   430       Data.get (Context.Proof lthy);
   426     fun infer (Abs (_, _, t)) = infer t
   431     fun infer (Abs (_, _, t)) = infer t
   427       | infer (Const (@{const_name Set.member}, _) $ t $ u) =
   432       | infer (Const (@{const_name Set.member}, _) $ t $ u) =
   428           infer_arities thy set_arities (SOME (HOLogic.flat_tuple_paths t), u)
   433           infer_arities thy set_arities (SOME (HOLogic.flat_tuple_paths t), u)
   429       | infer (t $ u) = infer t #> infer u
   434       | infer (t $ u) = infer t #> infer u
   430       | infer _ = I;
   435       | infer _ = I;