let compare eq1 eq2 =
match meta_convertibility_eq eq1 eq2 with
| true -> 0
- | false -> Pervasives.compare eq1 eq2
+ | false ->
+ let _, (ty, left, right), _, _ = eq1
+ and _, (ty', left', right'), _, _ = eq2 in
+ let weight_of t = fst (weight_of_term ~consider_metas:false t) in
+ let w1 = (weight_of ty) + (weight_of left) + (weight_of right)
+ and w2 = (weight_of ty') + (weight_of left') + (weight_of right') in
+ match Pervasives.compare w1 w2 with
+ | 0 -> Pervasives.compare eq1 eq2
+ | res -> res
end
module EqualitySet = Set.Make(OrderedEquality);;
-
+let weight_age_ratio = ref 0;; (* settable by the user from the command line *)
+let weight_age_counter = ref !weight_age_ratio;;
+
+let set_selection = ref (fun set -> EqualitySet.min_elt set);;
+
let select env passive =
- match passive with
- | hd::tl, pos -> (Negative, hd), (tl, pos)
- | [], hd::tl -> (Positive, hd), ([], tl)
- | _, _ -> assert false
+ let (neg_list, neg_set), (pos_list, pos_set) = passive in
+ if !weight_age_ratio > 0 then
+ weight_age_counter := !weight_age_counter - 1;
+ match !weight_age_counter with
+ | 0 -> (
+ weight_age_counter := !weight_age_ratio;
+ match neg_list, pos_list with
+ | hd::tl, pos ->
+ (Negative, hd), ((tl, EqualitySet.remove hd neg_set), (pos, pos_set))
+ | [], hd::tl ->
+ (Positive, hd), (([], neg_set), (tl, EqualitySet.remove hd pos_set))
+ | _, _ -> assert false
+ )
+ | _ ->
+ let remove eq l =
+ List.filter (fun e -> not (e = eq)) l
+ in
+ if EqualitySet.is_empty neg_set then
+ let current = !set_selection pos_set in
+ let passive =
+ (neg_list, neg_set),
+ (remove current pos_list, EqualitySet.remove current pos_set)
+ in
+ (Positive, current), passive
+ else
+ let current = !set_selection neg_set in
+ let passive =
+ (remove current neg_list, EqualitySet.remove current neg_set),
+ (pos_list, pos_set)
+ in
+ (Negative, current), passive
;;
-(*
-let select env passive =
- match passive with
- | neg, pos when EqualitySet.is_empty neg ->
- let elem = EqualitySet.min_elt pos in
- (Positive, elem), (neg, EqualitySet.remove elem pos)
- | neg, pos ->
- let elem = EqualitySet.min_elt neg in
- (Negative, elem), (EqualitySet.remove elem neg, pos)
+let make_passive neg pos =
+ let set_of equalities =
+ List.fold_left (fun s e -> EqualitySet.add e s) EqualitySet.empty equalities
+ in
+ (neg, set_of neg), (pos, set_of pos)
+;;
+
+
+let add_to_passive passive (new_neg, new_pos) =
+ let (neg_list, neg_set), (pos_list, pos_set) = passive in
+ let ok set equality = not (EqualitySet.mem equality set) in
+ let neg = List.filter (ok neg_set) new_neg
+ and pos = List.filter (ok pos_set) new_pos in
+ let add set equalities =
+ List.fold_left (fun s e -> EqualitySet.add e s) set equalities
+ in
+ (neg @ neg_list, add neg_set neg), (pos_list @ pos, add pos_set pos)
+;;
+
+
+let passive_is_empty = function
+ | ([], _), ([], _) -> true
+ | _ -> false
;;
-*)
(* TODO: find a better way! *)
;;
-let add_to_passive (passive_neg, passive_pos) (new_neg, new_pos) =
- let find sign eq1 eq2 =
- if meta_convertibility_eq eq1 eq2 then (
-(* Printf.printf "Trovato equazione duplicata di segno %s\n%s\n\n" *)
-(* (string_of_sign sign) (string_of_equality eq1); *)
- true
- ) else
- false
- in
- let ok sign equalities equality =
- not (List.exists (find sign equality) equalities)
- in
- let neg = List.filter (ok Negative passive_neg) new_neg in
- let pos = List.filter (ok Positive passive_pos) new_pos in
-(* let neg, pos = new_neg, new_pos in *)
- (neg @ passive_neg, passive_pos @ pos)
-;;
-
-
-let is_identity ((_, context, ugraph) as env) = function
- | ((_, (ty, left, right), _, _) as equality) ->
- let res =
- (left = right ||
- (fst (CicReduction.are_convertible context left right ugraph)))
- in
-(* if res then ( *)
-(* Printf.printf "is_identity: %s" (string_of_equality ~env equality); *)
-(* print_newline (); *)
-(* ); *)
- res
-;;
-
-
let forward_simplify env (sign, current) active =
-(* if sign = Negative then *)
-(* Some (sign, current) *)
-(* else *)
- let rec aux env (sign, current) =
- function
- | [] -> Some (sign, current)
- | (Negative, _)::tl -> aux env (sign, current) tl
- | (Positive, equality)::tl ->
- let newmeta, current = demodulation !maxmeta env current equality in
- maxmeta := newmeta;
- if is_identity env current then
- None
- else
- aux env (sign, current) tl
+ (* first step, remove already present equalities *)
+ let duplicate =
+ let rec aux = function
+ | [] -> false
+ | (s, eq)::tl when s = sign ->
+ if meta_convertibility_eq current eq then true
+ else aux tl
+ | _::tl -> aux tl
+ in
+ aux active
+ in
+ if duplicate then
+ None
+ else
+ let rec aux env (sign, current) = function
+ | [] -> Some (sign, current)
+ | (Negative, _)::tl -> aux env (sign, current) tl
+ | (Positive, equality)::tl ->
+ let newmeta, current =
+ demodulation !maxmeta env current equality in
+ maxmeta := newmeta;
+ if is_identity env current then
+ None
+ else
+ aux env (sign, current) tl
in
aux env (sign, current) active
;;
(fun (s, eq) res -> if find eq res then res else (s, eq)::res)
active []
;;
-
-
-(*
-let add_to_passive (passive_neg, passive_pos) (new_neg, new_pos) =
- let add_all = List.fold_left (fun res eq -> EqualitySet.add eq res) in
- add_all passive_neg new_neg, add_all passive_pos new_pos
-;;
-*)
let rec given_clause env passive active =
- match passive with
-(* | s1, s2 when (EqualitySet.is_empty s1) && (EqualitySet.is_empty s2) -> *)
-(* Failure *)
- | [], [] -> Failure
- | passive ->
+ match passive_is_empty passive with
+ | true -> Failure
+ | false ->
(* Printf.printf "before select\n"; *)
let (sign, current), passive = select env passive in
(* Printf.printf "before simplification: sign: %s\ncurrent: %s\n\n" *)
let proof, _, _, _ = current in
Success (Some proof, env)
| None ->
- Printf.printf "avanti... %s %s" (string_of_sign sign)
- (string_of_equality ~env current);
- print_newline ();
+(* Printf.printf "avanti... %s %s" (string_of_sign sign) *)
+(* (string_of_equality ~env current); *)
+(* print_newline (); *)
given_clause env passive active
| Some (sign, current) ->
-(* Printf.printf "sign: %s\ncurrent: %s\n" *)
+(* Printf.printf "selected: %s %s" *)
(* (string_of_sign sign) (string_of_equality ~env current); *)
(* print_newline (); *)
let new' = infer env sign current active in
+ let new' = forward_simplify_new env new' active in
+
let active =
backward_simplify env (sign, current) active
(* match new' with *)
(* | _ -> active *)
in
- let new' = forward_simplify_new env new' active in
-
print_endline "\n================================================";
let _ =
Printf.printf "active:\n%s\n"
(string_of_equality ~env e)) active)));
print_newline ();
in
+
(* let _ = *)
(* match new' with *)
(* | neg, pos -> *)
let term_equality = equality_of_term meta_proof goal in
let meta_proof, (eq_ty, left, right), _, _ = term_equality in
let active = [] in
-(* let passive = *)
-(* (EqualitySet.singleton term_equality, *)
-(* List.fold_left *)
-(* (fun res eq -> EqualitySet.add eq res) EqualitySet.empty equalities) *)
-(* in *)
- let passive = [term_equality], equalities in
+ let passive = make_passive [term_equality] equalities in
Printf.printf "\ncurrent goal: %s ={%s} %s\n"
(PP.ppterm left) (PP.ppterm eq_ty) (PP.ppterm right);
Printf.printf "\ncontext:\n%s\n" (PP.ppcontext context);
;;
+let configuration_file = ref "../../gTopLevel/gTopLevel.conf.xml";;
+
let _ =
- let configuration_file = "../../gTopLevel/gTopLevel.conf.xml" in
- Helm_registry.load_from configuration_file
+ let set_ratio v = weight_age_ratio := v; weight_age_counter := v
+ and set_sel () = set_selection := (fun s -> EqualitySet.max_elt s)
+ and set_conf f = configuration_file := f
+ in
+ Arg.parse [
+ "-r", Arg.Int set_ratio, "Weight-Age equality selection ratio";
+
+ "-i", Arg.Unit set_sel,
+ "Inverse selection (select heaviest equalities before)";
+
+ "-c", Arg.String set_conf, "Configuration file (for the db connection)";
+ ] (fun a -> ()) "Usage:"
in
+Helm_registry.load_from !configuration_file;
main ()