126 fun invalid_map ctxt t = |
126 fun invalid_map ctxt t = |
127 error ("Invalid map function in " ^ quote (Syntax.string_of_term ctxt t)); |
127 error ("Invalid map function in " ^ quote (Syntax.string_of_term ctxt t)); |
128 fun unexpected_corec_call ctxt t = |
128 fun unexpected_corec_call ctxt t = |
129 error ("Unexpected corecursive call: " ^ quote (Syntax.string_of_term ctxt t)); |
129 error ("Unexpected corecursive call: " ^ quote (Syntax.string_of_term ctxt t)); |
130 |
130 |
131 fun sort_list_duplicates xs = map snd (sort (int_ord o pairself fst) xs); |
131 fun sort_list_duplicates xs = map snd (sort (int_ord o apply2 fst) xs); |
132 |
132 |
133 val mk_conjs = try (foldr1 HOLogic.mk_conj) #> the_default @{const True}; |
133 val mk_conjs = try (foldr1 HOLogic.mk_conj) #> the_default @{const True}; |
134 val mk_disjs = try (foldr1 HOLogic.mk_disj) #> the_default @{const False}; |
134 val mk_disjs = try (foldr1 HOLogic.mk_disj) #> the_default @{const False}; |
135 val mk_dnf = mk_disjs o map mk_conjs; |
135 val mk_dnf = mk_disjs o map mk_conjs; |
136 |
136 |
413 nested_to_mutual_fps (K true) Greatest_FP bs res_Ts callers callssss0 lthy0; |
413 nested_to_mutual_fps (K true) Greatest_FP bs res_Ts callers callssss0 lthy0; |
414 |
414 |
415 val coinduct_attrs_pair = |
415 val coinduct_attrs_pair = |
416 (case gfp_sugar_thms of SOME ((_, attrs_pair), _, _, _, _) => attrs_pair | NONE => ([], [])); |
416 (case gfp_sugar_thms of SOME ((_, attrs_pair), _, _, _, _) => attrs_pair | NONE => ([], [])); |
417 |
417 |
418 val perm_fp_sugars = sort (int_ord o pairself #fp_res_index) fp_sugars; |
418 val perm_fp_sugars = sort (int_ord o apply2 #fp_res_index) fp_sugars; |
419 |
419 |
420 val indices = map #fp_res_index fp_sugars; |
420 val indices = map #fp_res_index fp_sugars; |
421 val perm_indices = map #fp_res_index perm_fp_sugars; |
421 val perm_indices = map #fp_res_index perm_fp_sugars; |
422 |
422 |
423 val perm_fpTs = map #T perm_fp_sugars; |
423 val perm_fpTs = map #T perm_fp_sugars; |
996 orelse primcorec_error_eqns ("missing equations for function(s): " ^ commas missing) [] |
996 orelse primcorec_error_eqns ("missing equations for function(s): " ^ commas missing) [] |
997 end; |
997 end; |
998 |
998 |
999 val callssss = |
999 val callssss = |
1000 map_filter (try (fn Sel x => x)) eqns_data |
1000 map_filter (try (fn Sel x => x)) eqns_data |
1001 |> partition_eq (op = o pairself #fun_name) |
1001 |> partition_eq (op = o apply2 #fun_name) |
1002 |> fst o finds (fn (x, ({fun_name, ...} :: _)) => x = fun_name) fun_names |
1002 |> fst o finds (fn (x, ({fun_name, ...} :: _)) => x = fun_name) fun_names |
1003 |> map (flat o snd) |
1003 |> map (flat o snd) |
1004 |> map2 (fold o find_corec_calls lthy has_call) basic_ctr_specss |
1004 |> map2 (fold o find_corec_calls lthy has_call) basic_ctr_specss |
1005 |> map2 (curry (op |>)) (map (map (fn {ctr, sels, ...} => |
1005 |> map2 (curry (op |>)) (map (map (fn {ctr, sels, ...} => |
1006 (ctr, map (K []) sels))) basic_ctr_specss); |
1006 (ctr, map (K []) sels))) basic_ctr_specss); |
1010 corec_specs_of bs arg_Ts res_Ts frees callssss lthy; |
1010 corec_specs_of bs arg_Ts res_Ts frees callssss lthy; |
1011 val corec_specs = take actual_nn corec_specs'; |
1011 val corec_specs = take actual_nn corec_specs'; |
1012 val ctr_specss = map #ctr_specs corec_specs; |
1012 val ctr_specss = map #ctr_specs corec_specs; |
1013 |
1013 |
1014 val disc_eqnss' = map_filter (try (fn Disc x => x)) eqns_data |
1014 val disc_eqnss' = map_filter (try (fn Disc x => x)) eqns_data |
1015 |> partition_eq (op = o pairself #fun_name) |
1015 |> partition_eq (op = o apply2 #fun_name) |
1016 |> fst o finds (fn (x, ({fun_name, ...} :: _)) => x = fun_name) fun_names |
1016 |> fst o finds (fn (x, ({fun_name, ...} :: _)) => x = fun_name) fun_names |
1017 |> map (sort (op < o pairself #ctr_no |> make_ord) o flat o snd); |
1017 |> map (sort (op < o apply2 #ctr_no |> make_ord) o flat o snd); |
1018 |
1018 |
1019 val _ = disc_eqnss' |> map (fn x => |
1019 val _ = disc_eqnss' |> map (fn x => |
1020 let val d = duplicates (op = o pairself #ctr_no) x in null d orelse |
1020 let val d = duplicates (op = o apply2 #ctr_no) x in |
1021 (if forall (is_some o #ctr_rhs_opt) x then |
1021 null d orelse |
1022 primcorec_error_eqns "multiple equations for constructor(s)" |
1022 (if forall (is_some o #ctr_rhs_opt) x then |
1023 (maps (fn t => filter (curry (op =) (#ctr_no t) o #ctr_no) x) d |
1023 primcorec_error_eqns "multiple equations for constructor(s)" |
1024 |> map (the o #ctr_rhs_opt)) else |
1024 (maps (fn t => filter (curry (op =) (#ctr_no t) o #ctr_no) x) d |
1025 primcorec_error_eqns "excess discriminator formula in definition" |
1025 |> map (the o #ctr_rhs_opt)) |
1026 (maps (fn t => filter (curry (op =) (#ctr_no t) o #ctr_no) x) d |> map #user_eqn)) end); |
1026 else |
|
1027 primcorec_error_eqns "excess discriminator formula in definition" |
|
1028 (maps (fn t => filter (curry (op =) (#ctr_no t) o #ctr_no) x) d |> map #user_eqn)) |
|
1029 end); |
1027 |
1030 |
1028 val sel_eqnss = map_filter (try (fn Sel x => x)) eqns_data |
1031 val sel_eqnss = map_filter (try (fn Sel x => x)) eqns_data |
1029 |> partition_eq (op = o pairself #fun_name) |
1032 |> partition_eq (op = o apply2 #fun_name) |
1030 |> fst o finds (fn (x, ({fun_name, ...} :: _)) => x = fun_name) fun_names |
1033 |> fst o finds (fn (x, ({fun_name, ...} :: _)) => x = fun_name) fun_names |
1031 |> map (flat o snd); |
1034 |> map (flat o snd); |
1032 |
1035 |
1033 val arg_Tss = map (binder_types o snd o fst) fixes; |
1036 val arg_Tss = map (binder_types o snd o fst) fixes; |
1034 val disc_eqnss = @{map 6} mk_actual_disc_eqns bs arg_Tss exhaustives corec_specs sel_eqnss |
1037 val disc_eqnss = @{map 6} mk_actual_disc_eqns bs arg_Tss exhaustives corec_specs sel_eqnss |
1314 NONE => [] |
1317 NONE => [] |
1315 | SOME (exhaustive_code, rhs, raw_rhs, ctr_thms) => |
1318 | SOME (exhaustive_code, rhs, raw_rhs, ctr_thms) => |
1316 let |
1319 let |
1317 val ms = map (Logic.count_prems o prop_of) ctr_thms; |
1320 val ms = map (Logic.count_prems o prop_of) ctr_thms; |
1318 val (raw_goal, goal) = (raw_rhs, rhs) |
1321 val (raw_goal, goal) = (raw_rhs, rhs) |
1319 |> pairself (curry mk_Trueprop_eq (applied_fun_of fun_name fun_T fun_args) |
1322 |> apply2 (curry mk_Trueprop_eq (applied_fun_of fun_name fun_T fun_args) |
1320 #> curry Logic.list_all (map dest_Free fun_args)); |
1323 #> curry Logic.list_all (map dest_Free fun_args)); |
1321 val (distincts, discIs, _, split_sels, split_sel_asms) = |
1324 val (distincts, discIs, _, split_sels, split_sel_asms) = |
1322 case_thms_of_term lthy raw_rhs; |
1325 case_thms_of_term lthy raw_rhs; |
1323 |
1326 |
1324 val raw_code_thm = mk_primcorec_raw_code_tac lthy distincts discIs split_sels |
1327 val raw_code_thm = mk_primcorec_raw_code_tac lthy distincts discIs split_sels |
1370 |> map sort_list_duplicates; |
1373 |> map sort_list_duplicates; |
1371 |
1374 |
1372 val ctr_alists = @{map 6} (fn disc_alist => maps oooo prove_ctr disc_alist) disc_alists |
1375 val ctr_alists = @{map 6} (fn disc_alist => maps oooo prove_ctr disc_alist) disc_alists |
1373 (map (map snd) sel_alists) corec_specs disc_eqnss sel_eqnss ctr_specss; |
1376 (map (map snd) sel_alists) corec_specs disc_eqnss sel_eqnss ctr_specss; |
1374 val ctr_thmss0 = map (map snd) ctr_alists; |
1377 val ctr_thmss0 = map (map snd) ctr_alists; |
1375 val ctr_thmss = map (map (snd o snd) o sort (int_ord o pairself fst)) ctr_alists; |
1378 val ctr_thmss = map (map (snd o snd) o sort (int_ord o apply2 fst)) ctr_alists; |
1376 |
1379 |
1377 val code_thmss = |
1380 val code_thmss = |
1378 @{map 6} prove_code exhaustives disc_eqnss sel_eqnss nchotomy_thmss ctr_thmss0 ctr_specss; |
1381 @{map 6} prove_code exhaustives disc_eqnss sel_eqnss nchotomy_thmss ctr_thmss0 ctr_specss; |
1379 |
1382 |
1380 val disc_iff_or_disc_thmss = |
1383 val disc_iff_or_disc_thmss = |