]> matita.cs.unibo.it Git - helm.git/blobdiff - helm/ocaml/mathql_interpreter/mQueryInterpreter.ml
patched and some funtions added
[helm.git] / helm / ocaml / mathql_interpreter / mQueryInterpreter.ml
index 5816a99bc10ae7def653c5558e1faa7a8b9d5f9c..a459fe82954e9eaa02ca09e9c3d07bac31712dad 100644 (file)
  * http://cs.unibo.it/helm/.
  *)
 
-(* contexts *****************************************************************)
+(*  AUTOR: Ferruccio Guidi <fguidi@cs.unibo.it>
+ *)
+
+exception Found
+
+module M = MathQL
+module P = MQueryUtil 
+module C = MQIConn
+module U = MQIUtil
+module L = MQILib
+module F = MQueryIO
 
-type svar_context = (MathQL.svar * MathQL.resource_set) list
+(* contexts *****************************************************************)
 
-type avar_context = (MathQL.avar * MathQL.resource) list
+type svar_context = (M.svar * M.resource_set) list
 
-type group_context = (MathQL.avar * MathQL.attribute_group) list
+type avar_context = (M.avar * M.resource) list
 
-type vvar_context = (MathQL.vvar * MathQL.value) list
+type group_context = (M.avar * M.attribute_group) list
 
 type context = {svars: svar_context;   
                 avars: avar_context;   
-                groups: group_context; (* auxiliary context *)
-                vvars: vvar_context  
+                groups: group_context (* auxiliary context *)  
                }
-
-(* execute  *****************************************************************)
-
-exception Found
-
-module M = MathQL
-module P = MQueryUtil 
-module C = MQIConn
-module U = MQIUtil
+              
+(* execute ******************************************************************)
 
 let execute h x =
    let warn q = 
      if C.set h C.Warn then 
      begin
         C.log h "MQIExecute: waring: reference to undefined variables: ";
-       P.text_of_query (C.log h) q "\n"
+       F.text_of_query (C.log h) "\n" q
      end
    in
-   let rec eval_val c = function
-      | M.False -> U.mql_false
-      | M.True -> U.mql_true
-      | M.Const s -> [s]
-      | M.Set l -> U.iter (eval_val c) l
-      | M.Test k y1 y2 ->
-         let cand y1 y2 =
-           if eval_val c y1 = U.mql_false then U.mql_false else eval_val c y2
-        in
-        let cor y1 y2 =
-            let v1 = eval_val c y1 in
-           if v1 = U.mql_false then eval_val c y2 else v1
-        in
-        let h f y1 y2 = f (eval_val c y1) (eval_val c y2) in
-         let f = match k with
-           | M.And  -> cand
-           | M.Or   -> cor
-           | M.Xor  -> h U.xor
-           | M.Sub  -> h U.set_sub
-           | M.Meet -> h U.set_meet
-           | M.Eq   -> h U.set_eq
-           | M.Le   -> h U.le
-           | M.Lt   -> h U.lt
-        in
-         f y1 y2 
-      | M.Not y -> 
-         if eval_val c y = U.mql_false then U.mql_true else U.mql_false
-      | M.VVar i -> begin
-         try List.assoc i c.vvars 
-         with Not_found -> warn (M.Subj (M.VVar i)); [] end
+   let proj v = List.map fst v in
+   let rec eval_query c = function
+      | M.Const r -> r
       | M.Dot i p -> begin
-         try List.assoc p (List.assoc i c.groups) 
-        with Not_found -> warn (M.Subj (M.Dot i p)); [] end
-      | M.Proj None x -> List.map (fun (r, _) -> r) (eval_query c x)
-      | M.Proj (Some p) x -> 
-         let proj_group_aux (q, v) = if q = p then v else [] in 
-         let proj_group a = U.iter proj_group_aux a in
-         let proj_set (_, g) = U.iter proj_group g in
-         U.iter proj_set (eval_query c x)
+         try U.mql_subj (List.assoc p (List.assoc i c.groups)) 
+        with Not_found -> warn (M.Dot i p); [] end
       | M.Ex l y -> 
          let rec ex_aux h = function
            | []        -> 
               let d = {c with groups = h} in
-               if eval_val d y = U.mql_false then () else raise Found 
+               if eval_query d y = U.mql_false then () else raise Found 
            | i :: tail -> 
                begin
                  try 
@@ -113,57 +82,15 @@ let execute h x =
               end
          in
         (try ex_aux [] l; U.mql_false with Found -> U.mql_true)
-      | M.StatVal y ->
-         let t = P.start_time () in
-        let r = (eval_val c y) in
-        let s = P.stop_time t in
-         C.log h (Printf.sprintf "Stat: %s,%i\n" s (List.length r));
-        r
-      | M.Count y -> [string_of_int (List.length (eval_val c y))]
-      | M.Align s y -> U.iter (U.align s) (eval_val c y)
-   and eval_query c = function
-      | M.Empty -> [] 
-      | M.Subj x ->
-         List.map (fun s -> (s, [])) (eval_val c x)
-      | M.Log _ b x ->
-         if b then begin
-           let t = P.start_time () in
-           P.text_of_query (C.log h) x "\n";
-           let s = P.stop_time t in
-           if C.set h C.Stat then 
-              C.log h (Printf.sprintf "Log source: %s\n" s);
-           eval_query c x
-        end else begin
-            let s = (eval_query c x) in
-           let t = P.start_time () in
-           P.text_of_result (C.log h) s "\n"; 
-           let r = P.stop_time t in
-           if C.set h C.Stat then 
-              C.log h (Printf.sprintf "Log: %s\n" r);
-           s
-        end
-      | M.If y x1 x2 ->
-         if (eval_val c y) = U.mql_false 
-           then (eval_query c x2) else (eval_query c x1)
-      | M.Bin k x1 x2 ->
-         let f = match k with
-           | M.BinFJoin -> U.mql_union
-           | M.BinFMeet -> U.mql_intersect
-           | M.BinFDiff -> U.mql_diff
-        in
-        f (eval_query c x1) (eval_query c x2) 
       | M.SVar i -> begin
          try List.assoc i c.svars 
         with Not_found -> warn (M.SVar i); [] end  
       | M.AVar i -> begin
          try [List.assoc i c.avars] 
         with Not_found -> warn (M.AVar i); [] end
-      | M.LetSVar i x1 x2 ->
-        let d = {c with svars = U.set (i, eval_query c x1) c.svars} in
+      | M.Let i x1 x2 ->
+        let d = {c with svars = P.add_assoc (i, eval_query c x1) c.svars} in
          eval_query d x2
-      | M.LetVVar i y x ->
-        let d = {c with vvars = U.set (i, eval_val c y) c.vvars} in
-         eval_query d x
       | M.For k i x1 x2 ->
          let f = match k with
            | M.GenFJoin -> U.mql_union
@@ -172,7 +99,7 @@ let execute h x =
          let rec for_aux = function
            | []     -> []
            | h :: t ->
-              let d = {c with avars = U.set (i, h) c.avars} in
+              let d = {c with avars = P.add_assoc (i, h) c.avars} in
               f (eval_query d x2) (for_aux t)
         in
         for_aux (eval_query c x1)
@@ -182,10 +109,10 @@ let execute h x =
         List.fold_right g (eval_query c x) []
       | M.Property q0 q1 q2 mc ct cfl el pat y ->
         let subj, mct = 
-           if q0 then [], (pat, q2 @ mc, eval_val c y)
-                 else (q2 @ mc), (pat, [], eval_val c y)  
+           if q0 then [], (pat, q2 @ mc, eval_query c y)
+                 else (q2 @ mc), (pat, [], eval_query c y)  
         in
-         let eval_cons (pat, p, y) = (pat, q2 @ p, eval_val c y) in
+         let eval_cons (pat, p, y) = (pat, q2 @ p, eval_query c y) in
         let cons_true = mct :: List.map eval_cons ct in
         let cons_false = List.map (List.map eval_cons) cfl in
         let eval_exp (p, po) = (q2 @ p, po) in
@@ -196,41 +123,29 @@ let execute h x =
          if C.set h C.Stat then 
            C.log h (Printf.sprintf "Property: %s,%i\n" s (List.length r));
         r 
-      | M.StatQuery x ->
-         let t = P.start_time () in
-        let r = (eval_query c x) in
-        let s = P.stop_time t in
-         C.log h (Printf.sprintf "Stat: %s,%i\n" s (List.length r));
-        r
       | M.Select i x y ->
          let rec select_aux = function
            | []     -> []
            | h :: t ->
-              let d = {c with avars = U.set (i, h) c.avars} in
-              if eval_val d y = U.mql_false 
+              let d = {c with avars = P.add_assoc (i, h) c.avars} in
+              if eval_query d y = U.mql_false 
                  then select_aux t else h :: select_aux t
         in
         select_aux (eval_query c x)
-      | M.Keep b l x -> 
-         let keep_path (p, v) t = 
-           if List.mem p l = b then t else (p, v) :: t in
-        let keep_grp a = List.fold_right keep_path a [] in
-         let keep_set a g = 
-           let kg = keep_grp a in
-           if kg = [] then g else kg :: g
-        in
-        let keep_av (s, g) = (s, List.fold_right keep_set g []) in
-        List.map keep_av (eval_query c x) 
+      | M.Fun p pl xl -> 
+         let e = {L.eval = eval_query c; L.conn = h} in
+         L.eval e (F.text_out_spec (C.log h) "\n") F.text_in_spec 
+            p pl xl
    and eval_grp c = function
       | M.Attr gs ->
-         let attr_aux g (p, y) = U.mql_union g [(p, eval_val c y)] in
+         let attr_aux g (p, y) = U.mql_union g [p, proj (eval_query c y)] in
         let attr_auxs s l = U.set_union s [List.fold_left attr_aux [] l] in
         List.fold_left attr_auxs [] gs
       | M.From i ->
          try snd (List.assoc i c.avars) 
         with Not_found -> warn (M.AVar i); []
    in
-   let c = {svars = []; avars = []; groups = []; vvars = []} in
+   let c = {svars = []; avars = []; groups = []} in
    let t = P.start_time () in
    let r = eval_query c x in
    let s = P.stop_time t in