src/HOL/Tools/Metis/metis_reconstruct.ML
changeset 40258 2c0d8fe36c21
parent 40221 d10b68c6e6d4
child 40259 c0e34371c2e2
equal deleted inserted replaced
40257:323f7aad54b0 40258:2c0d8fe36c21
   607       | (Var _, _) => add_terms (t, u)
   607       | (Var _, _) => add_terms (t, u)
   608       | (_, Var _) => add_terms (u, t)
   608       | (_, Var _) => add_terms (u, t)
   609       | _ => if untyped_aconv t u then I else raise TERM ("unify_terms", [t, u])
   609       | _ => if untyped_aconv t u then I else raise TERM ("unify_terms", [t, u])
   610   in th |> term_instantiate thy (unify_terms (prem, concl) []) end
   610   in th |> term_instantiate thy (unify_terms (prem, concl) []) end
   611 
   611 
   612 fun shuffle_key (((axiom_no, (_, index_no)), _), _) = (index_no, axiom_no)
       
   613 fun shuffle_ord p =
       
   614   rev_order (prod_ord int_ord int_ord (pairself shuffle_key p))
       
   615 
       
   616 val copy_prem = @{lemma "P ==> (P ==> P ==> Q) ==> Q" by fast}
   612 val copy_prem = @{lemma "P ==> (P ==> P ==> Q) ==> Q" by fast}
   617 
   613 
   618 fun copy_prems_tac [] ns i =
   614 fun copy_prems_tac [] ns i =
   619     if forall (curry (op =) 1) ns then all_tac else copy_prems_tac (rev ns) [] i
   615     if forall (curry (op =) 1) ns then all_tac else copy_prems_tac (rev ns) [] i
   620   | copy_prems_tac (1 :: ms) ns i =
   616   | copy_prems_tac (1 :: ms) ns i =
   621     rotate_tac 1 i THEN copy_prems_tac ms (1 :: ns) i
   617     rotate_tac 1 i THEN copy_prems_tac ms (1 :: ns) i
   622   | copy_prems_tac (m :: ms) ns i =
   618   | copy_prems_tac (m :: ms) ns i =
   623     etac copy_prem i THEN copy_prems_tac ms (m div 2 :: (m + 1) div 2 :: ns) i
   619     etac copy_prem i THEN copy_prems_tac ms (m div 2 :: (m + 1) div 2 :: ns) i
   624 
   620 
   625 fun instantiate_forall_tac thy params t i =
   621 fun instantiate_forall_tac thy t i st =
   626   let
   622   let
       
   623     val params = Logic.strip_params (Logic.get_goal (prop_of st) i) |> rev
   627     fun repair (t as (Var ((s, _), _))) =
   624     fun repair (t as (Var ((s, _), _))) =
   628         (case find_index (fn ((s', _), _) => s' = s) params of
   625         (case find_index (fn (s', _) => s' = s) params of
   629            ~1 => t
   626            ~1 => t
   630          | j => Bound j)
   627          | j => Bound j)
   631       | repair (t $ u) = repair t $ repair u
   628       | repair (t $ u) = repair t $ repair u
   632       | repair t = t
   629       | repair t = t
   633     val t' = t |> repair |> fold (curry absdummy) (map snd params)
   630     val t' = t |> repair |> fold (curry absdummy) (map snd params)
   634     fun do_instantiate th =
   631     fun do_instantiate th =
   635       let val var = Term.add_vars (prop_of th) [] |> the_single in
   632       let val var = Term.add_vars (prop_of th) [] |> the_single in
   636         th |> term_instantiate thy [(Var var, t')]
   633         th |> term_instantiate thy [(Var var, t')]
   637       end
   634       end
   638   in
   635   in
   639     etac @{thm allE} i
   636     (etac @{thm allE} i
   640     THEN rotate_tac ~1 i
   637      THEN rotate_tac ~1 i
   641     THEN PRIMITIVE do_instantiate
   638      THEN PRIMITIVE do_instantiate) st
   642   end
   639   end
   643 
   640 
   644 fun release_clusters_tac _ _ _ _ [] = K all_tac
   641 fun release_clusters_tac _ _ _ [] = K all_tac
   645   | release_clusters_tac thy ax_counts substs params
   642   | release_clusters_tac thy ax_counts substs
   646                          ((ax_no, cluster_no) :: clusters) =
   643                          ((ax_no, cluster_no) :: clusters) =
   647     let
   644     let
   648       fun in_right_cluster s =
   645       fun in_right_cluster s =
   649         (s |> Meson_Clausify.cluster_of_zapped_var_name |> fst |> snd |> fst)
   646         (s |> Meson_Clausify.cluster_of_zapped_var_name |> fst |> snd |> fst)
   650         = cluster_no
   647         = cluster_no
   655                             tsubst |> filter (in_right_cluster
   652                             tsubst |> filter (in_right_cluster
   656                                               o fst o fst o dest_Var o fst)
   653                                               o fst o fst o dest_Var o fst)
   657                                    |> map snd |> SOME
   654                                    |> map snd |> SOME
   658                            else
   655                            else
   659                              NONE)
   656                              NONE)
   660       val n = length cluster_substs
       
   661       fun do_cluster_subst cluster_subst =
   657       fun do_cluster_subst cluster_subst =
   662         map (instantiate_forall_tac thy params) cluster_subst @ [rotate_tac 1]
   658         map (instantiate_forall_tac thy) cluster_subst @ [rotate_tac 1]
   663       val params' = params (* FIXME ### existentials! *)
       
   664       val first_prem = find_index (fn (ax_no', _) => ax_no' = ax_no) substs
   659       val first_prem = find_index (fn (ax_no', _) => ax_no' = ax_no) substs
   665     in
   660     in
   666       rotate_tac first_prem
   661       rotate_tac first_prem
   667       THEN' (EVERY' (maps do_cluster_subst cluster_substs))
   662       THEN' (EVERY' (maps do_cluster_subst cluster_substs))
   668       THEN' rotate_tac (~ first_prem - length cluster_substs)
   663       THEN' rotate_tac (~ first_prem - length cluster_substs)
   669       THEN' release_clusters_tac thy ax_counts substs params' clusters
   664       THEN' release_clusters_tac thy ax_counts substs clusters
   670     end
   665     end
   671 
   666 
   672 val cluster_ord =
   667 val cluster_ord =
   673   prod_ord (prod_ord int_ord (prod_ord int_ord int_ord)) bool_ord
   668   prod_ord (prod_ord int_ord (prod_ord int_ord int_ord)) bool_ord
   674 
   669 
   680   Table(type key = int * (indexname * (sort * typ)) list
   675   Table(type key = int * (indexname * (sort * typ)) list
   681         val ord = prod_ord int_ord tysubst_ord)
   676         val ord = prod_ord int_ord tysubst_ord)
   682 
   677 
   683 structure Int_Pair_Graph =
   678 structure Int_Pair_Graph =
   684   Graph(type key = int * int val ord = prod_ord int_ord int_ord)
   679   Graph(type key = int * int val ord = prod_ord int_ord int_ord)
       
   680 
       
   681 fun shuffle_key (((axiom_no, (_, index_no)), _), _) = (index_no, axiom_no)
       
   682 fun shuffle_ord p = prod_ord int_ord int_ord (pairself shuffle_key p)
   685 
   683 
   686 (* Attempts to derive the theorem "False" from a theorem of the form
   684 (* Attempts to derive the theorem "False" from a theorem of the form
   687    "P1 ==> ... ==> Pn ==> False", where the "Pi"s are to be discharged using the
   685    "P1 ==> ... ==> Pn ==> False", where the "Pi"s are to be discharged using the
   688    specified axioms. The axioms have leading "All" and "Ex" quantifiers, which
   686    specified axioms. The axioms have leading "All" and "Ex" quantifiers, which
   689    must be eliminated first. *)
   687    must be eliminated first. *)
   755         |> fold Int_Pair_Graph.add_deps_acyclic depss
   753         |> fold Int_Pair_Graph.add_deps_acyclic depss
   756         |> Int_Pair_Graph.topological_order
   754         |> Int_Pair_Graph.topological_order
   757         handle Int_Pair_Graph.CYCLES _ =>
   755         handle Int_Pair_Graph.CYCLES _ =>
   758                error "Cannot replay Metis proof in Isabelle without \
   756                error "Cannot replay Metis proof in Isabelle without \
   759                      \\"Hilbert_Choice\"."
   757                      \\"Hilbert_Choice\"."
   760       val params0 =
   758       val outer_param_names =
   761         [] |> fold (Term.add_vars o snd) (map_filter I axioms)
   759         [] |> fold (Term.add_var_names o snd) (map_filter I axioms)
   762            |> map (`(Meson_Clausify.cluster_of_zapped_var_name o fst o fst))
   760            |> map (`(Meson_Clausify.cluster_of_zapped_var_name o fst))
   763            |> filter (fn (((_, (cluster_no, _)), skolem), _) =>
   761            |> filter (fn (((_, (cluster_no, _)), skolem), _) =>
   764                          cluster_no = 0 andalso skolem)
   762                          cluster_no = 0 andalso skolem)
   765            |> sort shuffle_ord |> map snd
   763            |> sort shuffle_ord |> map (fst o snd)
   766       val ax_counts =
   764       val ax_counts =
   767         Int_Tysubst_Table.empty
   765         Int_Tysubst_Table.empty
   768         |> fold (fn (ax_no, (_, (tysubst, _))) =>
   766         |> fold (fn (ax_no, (_, (tysubst, _))) =>
   769                     Int_Tysubst_Table.map_default ((ax_no, tysubst), 0)
   767                     Int_Tysubst_Table.map_default ((ax_no, tysubst), 0)
   770                                                   (Integer.add 1)) substs
   768                                                   (Integer.add 1)) substs
   775         "; tysubst: " ^ PolyML.makestring tysubst ^ "; tsubst: {" ^
   773         "; tysubst: " ^ PolyML.makestring tysubst ^ "; tsubst: {" ^
   776         commas (map ((fn (s, t) => s ^ " |-> " ^ t)
   774         commas (map ((fn (s, t) => s ^ " |-> " ^ t)
   777                      o pairself (Syntax.string_of_term ctxt)) tsubst) ^ "}"
   775                      o pairself (Syntax.string_of_term ctxt)) tsubst) ^ "}"
   778       val _ = tracing ("SUBSTS (" ^ string_of_int (length substs) ^ "):\n" ^
   776       val _ = tracing ("SUBSTS (" ^ string_of_int (length substs) ^ "):\n" ^
   779                        cat_lines (map string_for_subst_info substs))
   777                        cat_lines (map string_for_subst_info substs))
   780       val _ = tracing ("OUTERMOST SKOLEMS: " ^ PolyML.makestring params0)
       
   781       val _ = tracing ("ORDERED CLUSTERS: " ^ PolyML.makestring ordered_clusters)
   778       val _ = tracing ("ORDERED CLUSTERS: " ^ PolyML.makestring ordered_clusters)
       
   779       val _ = tracing ("OUTER PARAMS: " ^ PolyML.makestring outer_param_names)
   782       val _ = tracing ("AXIOM COUNTS: " ^ PolyML.makestring ax_counts)
   780       val _ = tracing ("AXIOM COUNTS: " ^ PolyML.makestring ax_counts)
   783 *)
   781 *)
   784       fun rotation_for_subgoal i =
   782       fun rotation_for_subgoal i =
   785         find_index (fn (_, (subgoal_no, _)) => subgoal_no = i) substs
   783         find_index (fn (_, (subgoal_no, _)) => subgoal_no = i) substs
   786     in
   784     in
   787       Goal.prove ctxt [] [] @{prop False}
   785       Goal.prove ctxt [] [] @{prop False}
   788           (K (cut_rules_tac
   786           (K (cut_rules_tac
   789                   (map (fst o the o nth axioms o fst o fst) ax_counts) 1
   787                   (map (fst o the o nth axioms o fst o fst) ax_counts) 1
   790               THEN TRY (REPEAT_ALL_NEW (etac @{thm exE}) 1)
   788               THEN TRY (REPEAT_ALL_NEW (etac @{thm exE}) 1)
       
   789               THEN rename_tac outer_param_names 1
   791               THEN copy_prems_tac (map snd ax_counts) [] 1
   790               THEN copy_prems_tac (map snd ax_counts) [] 1
   792               THEN release_clusters_tac thy ax_counts substs params0
   791               THEN release_clusters_tac thy ax_counts substs ordered_clusters 1
   793                                         ordered_clusters 1
       
   794               THEN match_tac [prems_imp_false] 1
   792               THEN match_tac [prems_imp_false] 1
   795               THEN ALLGOALS (fn i =>
   793               THEN ALLGOALS (fn i =>
   796                        rtac @{thm Meson.skolem_COMBK_I} i
   794                        rtac @{thm Meson.skolem_COMBK_I} i
   797                        THEN rotate_tac (rotation_for_subgoal i) i
   795                        THEN rotate_tac (rotation_for_subgoal i) i
   798 (*                       THEN PRIMITIVE (unify_first_prem_with_concl thy i) ###*)
   796 (*                       THEN PRIMITIVE (unify_first_prem_with_concl thy i) ### FIXME: needed? *)
   799                        THEN assume_tac i)))
   797                        THEN assume_tac i)))
   800       handle ERROR _ =>
   798       handle ERROR _ =>
   801              error ("Cannot replay Metis proof in Isabelle:\n\
   799              error ("Cannot replay Metis proof in Isabelle:\n\
   802                     \Error when discharging Skolem assumptions.")
   800                     \Error when discharging Skolem assumptions.")
   803     end
   801     end