src/Provers/induct_method.ML
changeset 15570 8d8c70b41bab
parent 15531 08c8dad8e399
child 15574 b1d1b5bfc464
equal deleted inserted replaced
15569:1b3115d1a8df 15570:8d8c70b41bab
    57           end
    57           end
    58       | prep_var (_, NONE) = NONE;
    58       | prep_var (_, NONE) = NONE;
    59     val xs = InductAttrib.vars_of tm;
    59     val xs = InductAttrib.vars_of tm;
    60   in
    60   in
    61     align "Rule has fewer variables than instantiations given" xs ts
    61     align "Rule has fewer variables than instantiations given" xs ts
    62     |> mapfilter prep_var
    62     |> List.mapPartial prep_var
    63   end;
    63   end;
    64 
    64 
    65 
    65 
    66 
    66 
    67 (** cases method **)
    67 (** cases method **)
    94     val cert = Thm.cterm_of sg;
    94     val cert = Thm.cterm_of sg;
    95 
    95 
    96     fun inst_rule r =
    96     fun inst_rule r =
    97       if null insts then RuleCases.add r
    97       if null insts then RuleCases.add r
    98       else (align_left "Rule has fewer premises than arguments given" (Thm.prems_of r) insts
    98       else (align_left "Rule has fewer premises than arguments given" (Thm.prems_of r) insts
    99         |> (flat o map (prep_inst align_left cert I))
    99         |> (List.concat o map (prep_inst align_left cert I))
   100         |> Drule.cterm_instantiate) r |> rpair (RuleCases.get r);
   100         |> Drule.cterm_instantiate) r |> rpair (RuleCases.get r);
   101 
   101 
   102     val ruleq =
   102     val ruleq =
   103       (case opt_rule of
   103       (case opt_rule of
   104         NONE =>
   104         NONE =>
   106             Method.trace ctxt rules;
   106             Method.trace ctxt rules;
   107             Seq.flat (Seq.map (Seq.try inst_rule) (Seq.of_list rules))
   107             Seq.flat (Seq.map (Seq.try inst_rule) (Seq.of_list rules))
   108           end
   108           end
   109       | SOME r => Seq.single (inst_rule r));
   109       | SOME r => Seq.single (inst_rule r));
   110 
   110 
   111     fun prep_rule (th, (cases, n)) = Seq.map (apsnd (rpair (drop (n, facts))) o rpair cases)
   111     fun prep_rule (th, (cases, n)) = Seq.map (apsnd (rpair (Library.drop (n, facts))) o rpair cases)
   112       (Method.multi_resolves (take (n, facts)) [th]);
   112       (Method.multi_resolves (Library.take (n, facts)) [th]);
   113   in resolveq_cases_tac (RuleCases.make is_open NONE) (Seq.flat (Seq.map prep_rule ruleq)) end;
   113   in resolveq_cases_tac (RuleCases.make is_open NONE) (Seq.flat (Seq.map prep_rule ruleq)) end;
   114 
   114 
   115 in
   115 in
   116 
   116 
   117 val cases_meth = Method.METHOD_CASES o ((Seq.DETERM o HEADGOAL) oo cases_tac);
   117 val cases_meth = Method.METHOD_CASES o ((Seq.DETERM o HEADGOAL) oo cases_tac);
   159 
   159 
   160 fun imp_intr i raw_th =
   160 fun imp_intr i raw_th =
   161   let
   161   let
   162     val th = Thm.permute_prems (i - 1) 1 raw_th;
   162     val th = Thm.permute_prems (i - 1) 1 raw_th;
   163     val cprems = Drule.cprems_of th;
   163     val cprems = Drule.cprems_of th;
   164     val As = take (length cprems - 1, cprems);
   164     val As = Library.take (length cprems - 1, cprems);
   165     val C = Thm.cterm_of (Thm.sign_of_thm th) (Var (("C", #maxidx (Thm.rep_thm th) + 1), propT));
   165     val C = Thm.cterm_of (Thm.sign_of_thm th) (Var (("C", #maxidx (Thm.rep_thm th) + 1), propT));
   166     val dummy_st = Drule.mk_triv_goal (Drule.list_implies (As, C));
   166     val dummy_st = Drule.mk_triv_goal (Drule.list_implies (As, C));
   167   in th COMP Thm.lift_rule (dummy_st, 1) Data.local_impI end;
   167   in th COMP Thm.lift_rule (dummy_st, 1) Data.local_impI end;
   168 
   168 
   169 
   169 
   254       | rename_params ((y,Type(U,_))::ys) =
   254       | rename_params ((y,Type(U,_))::ys) =
   255           (if U=T then x else y)::rename_params ys
   255           (if U=T then x else y)::rename_params ys
   256       | rename_params ((y,_)::ys) = y::rename_params ys;
   256       | rename_params ((y,_)::ys) = y::rename_params ys;
   257     fun rename_asm (A:term):term = 
   257     fun rename_asm (A:term):term = 
   258       let val xs = rename_params (Logic.strip_params A)
   258       let val xs = rename_params (Logic.strip_params A)
   259           val xs' = case filter (equal x) xs of
   259           val xs' = case List.filter (equal x) xs of
   260                       [] => xs | [_] => xs | _ => index 1 xs
   260                       [] => xs | [_] => xs | _ => index 1 xs
   261       in Logic.list_rename_params (xs',A) end;
   261       in Logic.list_rename_params (xs',A) end;
   262     fun rename_prop (p:term) =
   262     fun rename_prop (p:term) =
   263       let val (As,C) = Logic.strip_horn p
   263       let val (As,C) = Logic.strip_horn p
   264       in Logic.list_implies(map rename_asm As, C) end;
   264       in Logic.list_implies(map rename_asm As, C) end;
   266     val thm' = equal_elim (reflexive cp') thm
   266     val thm' = equal_elim (reflexive cp') thm
   267   in Thm.put_name_tags (Thm.get_name_tags thm) thm' end
   267   in Thm.put_name_tags (Thm.get_name_tags thm) thm' end
   268   | rename _ thm = thm;
   268   | rename _ thm = thm;
   269 
   269 
   270 fun find_inductT ctxt insts =
   270 fun find_inductT ctxt insts =
   271   foldr multiply (insts |> mapfilter (fn [] => NONE | ts => last_elem ts)
   271   Library.foldr multiply (insts |> List.mapPartial (fn [] => NONE | ts => List.last ts)
   272     |> map (InductAttrib.find_inductT ctxt o fastype_of), [[]])
   272     |> map (InductAttrib.find_inductT ctxt o fastype_of), [[]])
   273   |> map join_rules |> flat |> map (rename insts);
   273   |> map join_rules |> List.concat |> map (rename insts);
   274 
   274 
   275 fun find_inductS ctxt (fact :: _) = InductAttrib.find_inductS ctxt fact
   275 fun find_inductS ctxt (fact :: _) = InductAttrib.find_inductS ctxt fact
   276   | find_inductS _ _ = [];
   276   | find_inductS _ _ = [];
   277 
   277 
   278 
   278 
   289 
   289 
   290     val inst_rule = apfst (fn r =>
   290     val inst_rule = apfst (fn r =>
   291       if null insts then r
   291       if null insts then r
   292       else (align_right "Rule has fewer conclusions than arguments given"
   292       else (align_right "Rule has fewer conclusions than arguments given"
   293           (Data.dest_concls (Thm.concl_of r)) insts
   293           (Data.dest_concls (Thm.concl_of r)) insts
   294         |> (flat o map (prep_inst align_right cert (atomize_term sg)))
   294         |> (List.concat o map (prep_inst align_right cert (atomize_term sg)))
   295         |> Drule.cterm_instantiate) r);
   295         |> Drule.cterm_instantiate) r);
   296 
   296 
   297     val ruleq =
   297     val ruleq =
   298       (case opt_rule of
   298       (case opt_rule of
   299         NONE =>
   299         NONE =>
   303             rules |> Seq.THEN (Seq.of_list, Seq.THEN (rule_versions, Seq.try inst_rule))
   303             rules |> Seq.THEN (Seq.of_list, Seq.THEN (rule_versions, Seq.try inst_rule))
   304           end
   304           end
   305       | SOME r => r |> Seq.THEN (rule_versions, Seq.single o inst_rule));
   305       | SOME r => r |> Seq.THEN (rule_versions, Seq.single o inst_rule));
   306 
   306 
   307     fun prep_rule (th, (cases, n)) =
   307     fun prep_rule (th, (cases, n)) =
   308       Seq.map (rpair (cases, n - length facts, drop (n, facts)))
   308       Seq.map (rpair (cases, n - length facts, Library.drop (n, facts)))
   309         (Method.multi_resolves (take (n, facts)) [th]);
   309         (Method.multi_resolves (Library.take (n, facts)) [th]);
   310     val tac = resolveq_cases_tac' RuleCases.make is_open (Seq.flat (Seq.map prep_rule ruleq));
   310     val tac = resolveq_cases_tac' RuleCases.make is_open (Seq.flat (Seq.map prep_rule ruleq));
   311   in tac THEN_ALL_NEW_CASES rulify_tac end;
   311   in tac THEN_ALL_NEW_CASES rulify_tac end;
   312 
   312 
   313 in
   313 in
   314 
   314