[m-dev.] for review: Aditi update documentation round 2

Simon Taylor stayl at cs.mu.OZ.AU
Fri Jul 2 16:58:47 AEST 1999


--- reference_manual.texi	1999/06/29 02:22:21	1.5
+++ reference_manual.texi	1999/07/02 06:53:39
@@ -5121,31 +5121,53 @@
 @subsubsection Aditi update syntax
 
 The Melbourne Mercury compiler provides special syntax to specify updates
-of Aditi base relations. For a predicate @samp{p/3}, the following update
-procedures are defined. Variables named @samp{DB at var{N}} are
- at samp{aditi__state} variables. When occuring as a pair at the end
-of an argument list, they have mode @samp{aditi_di, aditi_uo}.
+of Aditi base relations.
+
+Note: Only error checking is implemented for Aditi updates --- no code is
+generated yet.
+
+ at c XXX texinfo doesn't have subsubsubsection.
+ at ignore
+ at menu 
+* Aditi update notes::
+* Insertion::
+* Deletion::
+* Bulk insertion::
+* Bulk deletion::
+* Modification::
+ at end menu
+ at end ignore
+
+ at c @node Aditi update notes::
+ at subsubheading Aditi update notes
+
+There must be a @w{@samp{:- pragma base_relation}} declaration for
+any relation to be updated. 
 
 It is currently up to the application to ensure that any modifications
 do not change the determinism of a base relation. Updates of relations
-with unique B-tree indexes are checked to ensure that a key is not given
-multiple values. The transaction will abort if this occurs.
-
-Note: The implementation of Aditi updates is not yet complete.
+with unique B-tree indexes are checked to ensure that a key is not
+given multiple values. The transaction will abort if this occurs.
 
 The examples make use of the following declarations.
 @example
 :- pred p(aditi__state::aditi_ui, int::out, int::out) is nondet.
 :- pragma base_relation(p/3).
 
-:- func q(aditi__state::aditi_ui, int::out) = (int::out) is nondet.
-:- pragma base_relation(q/2).
+:- func f(aditi__state::aditi_ui, int::out) = (int::out) is nondet.
+:- pragma base_relation(f/2).
 
 :- pred ancestor(aditi__state::aditi_ui, int::out, int::out) is nondet.
 :- pragma aditi(ancestor/3).
 @end example
 
- at c XXX texinfo doesn't have subsubsubsection.
+Variables named @samp{DB at var{N}} are
+ at samp{aditi__state} variables. When occuring as a pair at the end
+of an argument list, they have mode @w{@samp{aditi_di, aditi_uo}}.
+
+Predicate and function names in Aditi update goals may be module qualified.
+
+ at c @node Insertion
 @subsubheading Insertion
 
 @example
@@ -5158,8 +5180,6 @@
 must have the same type signature as the relation. All the arguments
 of the tuple have mode @samp{in}, except the @samp{aditi__state} argument
 which has mode @samp{unused}.
-There must be a @w{@samp{:- pragma base_relation}} declaration for
- at w{@samp{@var{Name}/@var{Arity}}}.
 
 Note that @w{@samp{@var{PredName}(@var{Var1}, @var{Var2}, @dots{})}}
 in a call to @samp{aditi_insert} is not a higher-order term.
@@ -5168,17 +5188,20 @@
 
 Examples:
 @example
+insert_example_1(DB0, DB) :-
         aditi_insert(p(_, 1, 2), DB0, DB).
 
-        aditi_insert(q(_, 1) = 2, DB0, DB).
+insert_example_2(DB0, DB) :-
+        aditi_insert(f(_, 1) = 2, DB0, DB).
 @end example
 
+ at c @node Deletion
 @subsubheading Deletion
 
 @example
-aditi_delete(@var{PredName}(@var{Var1}, @var{Var2}, @dots{}) :- @var{Goal}, @var{DB0}, @var{DB}).
+aditi_delete((@var{PredName}(@var{Var1}, @var{Var2}, @dots{}) :- @var{Goal}), @var{DB0}, @var{DB}).
 
-aditi_delete(@var{FuncName}(@var{Var1}, @var{Var2}, @dots{}) = @var{RetVar} :- @var{Goal}, @var{DB0}, @var{DB}).
+aditi_delete((@var{FuncName}(@var{Var1}, @var{Var2}, @dots{}) = @var{RetVar} :- @var{Goal}), @var{DB0}, @var{DB}).
 
 aditi_delete(@var{PredOrFunc} @var{Name}/@var{Arity}, @var{Closure}, @var{DB0}, @var{DB}).
 @end example
@@ -5186,19 +5209,16 @@
 Delete all tuples for which @samp{@var{Goal}} or @samp{@var{Closure}} 
 succeeds from the named base relation. 
 
-There must be a @w{@samp{:- pragma base_relation}} declaration for
- at w{@samp{@var{PredOrFunc} @var{Name}/@var{Arity}}}.
-
 For the third alternative @samp{@var{PredOrFunc}} must be either
 @samp{pred} or @samp{func}.
 
-When updating a predicate with type declaration
+When deleting from a predicate with type declaration
 @w{@samp{:- pred p(aditi__state, @var{Type1}, @dots{})}},
 @samp{@var{Closure}} must have type
 @w{@samp{aditi_top_down pred(aditi__state, @var{Type1}, @dots{})}},
 and inst @w{@samp{pred(unused, in, @dots{}) is semidet}}.
 
-When updating a function with type declaration
+When deleting from a function with type declaration
 @w{@samp{:- func p(aditi__state, @var{Type1}, @dots{}) = @var{Type2}}},
 @samp{@var{Closure}} must have type
 @w{@samp{aditi_top_down func(aditi__state, @var{Type1}, @dots{}) = @var{Type2}}},
@@ -5209,7 +5229,7 @@
 Aditi database using the normal Mercury execution algorithm.
 
 The @samp{aditi__state} argument of @samp{@var{Closure}} must have
-mode @samp{unused} -- it is not possible to call an Aditi
+mode @samp{unused} --- it is not possible to call an Aditi
 relation from the deletion condition. All other arguments of
 @samp{@var{Closure}} must have mode @samp{in}.
 
@@ -5219,28 +5239,44 @@
 
 Examples:
 @example
+delete_example_1(DB0, DB) :-
         aditi_delete((p(_, X, Y) :- X + Y = 2), DB0, DB).
 
-        aditi_delete(q(_, 2) = Y, DB0, DB).
+delete_example_2(DB0, DB) :-
+        aditi_delete(f(_, 2) = _Y, DB0, DB).
 
+delete_example_3(DB0, DB) :-
         DeleteP = (aditi_top_down
                pred(_::unused, X::in, Y::in) is semidet :-
                         X = 2
                ),
         aditi_delete(pred p/3, DeleteP, DB0, DB).
 
+delete_example_4(DB0, DB) :-
         DeleteQ = (aditi_top_down
                func(_::unused, X::in) = (Y::in) is semidet :-
                         X = 2
                ),
-        aditi_delete(func q/2, DeleteQ, DB0, DB).
+        aditi_delete(func f/2, DeleteQ, DB0, DB).
+
+delete_example_5 -->
+	aditi_delete((p(_, X, Y) :- X = 2, Y = 2)). 
+		
 @end example
 
-The type of @samp{Pred} is
+The type of @samp{DeleteP} is
 @w{@samp{aditi_top_down pred(aditi__state, int, int)}}.
 Its inst is @w{@samp{pred(unused, in, in) is nondet}}, as for a normal
 lambda expression.
 
+Note that in @samp{delete_example_5} the extra set of parentheses around
+the goal are needed, otherwise the second goal in the conjunction
+in the deletion goal is parsed as an argument of the `aditi_delete' call.
+This behaviour is inconsistent with ISO Prolog syntax. An ISO Prolog
+implementation would report a syntax error without the extra set of
+parentheses.
+
+ at c @node Bulk insertion
 @subsubheading Bulk insertion
 
 @example
@@ -5249,10 +5285,8 @@
 
 Insert all solutions of @samp{@var{Closure}} into the named relation.
 @samp{@var{PredOrFunc}} must be either @samp{pred} or @samp{func}.
-There must be a @w{@samp{:- pragma base_relation}} declaration for
- at w{@samp{@var{Name}/@var{Arity}}}.
 
-The closure to produce the tuples to insert must have the same
+The closure for producing the tuples to insert must have the same
 type signature as the base relation, with all arguments except
 the @samp{aditi__state} output. It must also be evaluable bottom-up
 by the Aditi system. This means the predicate passed must have a
@@ -5262,14 +5296,17 @@
 
 Examples:
 @example
+bulk_insert_example_1(DB0, DB) :-
         aditi_bulk_insert(pred p/3, ancestor, DB0, DB).
 
+bulk_insert_example_2(DB0, DB) :-
         InsertP = (aditi_bottom_up
                 pred(DB1::aditi_ui, X::out, Y::out) is nondet :-
                         ancestor(DB1, X, Y)
                 ),
         aditi_bulk_insert(pred p/3, InsertP, DB0, DB).
 
+bulk_insert_example_3(DB0, DB) :-
         InsertQ = (aditi_bottom_up
                 func(DB1::aditi_ui, X::out) = (Y::out) is nondet :-
                         ancestor(DB1, X, Y)
@@ -5277,11 +5314,12 @@
         aditi_bulk_insert(pred p/3, InsertQ, DB0, DB).
 @end example
 
-The type of @samp{Pred} is
+The type of @samp{InsertP} is
 @w{@samp{aditi_bottom_up pred(aditi__state, int, int)}}.
 Its inst is @w{@samp{pred(aditi_ui, out, out) is nondet}},
 as for a normal lambda expression.
 
+ at c @node Bulk deletion
 @subsubheading Bulk deletion
 
 @example
@@ -5290,25 +5328,24 @@
 
 Delete all solutions of @samp{@var{Closure}} from the named relation.
 @samp{@var{PredOrFunc}} must be either @samp{pred} or @samp{func}.
-There must be a @w{@samp{:- pragma base_relation}} declaration for
- at w{@samp{@var{Name}/@var{Arity}}}.
 
-The restrictions on the closure term passed to @samp{aditi_bulk_insert} also
+The restrictions on the closure passed to @samp{aditi_bulk_insert} also
 apply to @samp{aditi_bulk_delete}.
 
+ at c @node Modification
 @subsubheading Modification
 
 @example
 aditi_modify(
         (@var{PredName}(@var{Var1}, @var{Var2}, @dots{}) ==> @var{Predname}(@var{Var3}, @var{Var4}, @dots{}) :-
-                @var{Goal},
+                @var{Goal}
         ),
         @var{DB0}, @var{DB}).
 
 aditi_modify(
         ((@var{FuncName}(@var{Var1}, @var{Var2}, @dots{}) = @var{RetVar0}) ==>
-                ((@var{Predname}(@var{Var3}, @var{Var4}, @dots{}) = @var{RetVar})) :-
-                @var{Goal},
+        (@var{Predname}(@var{Var3}, @var{Var4}, @dots{}) = @var{RetVar}) :-
+                @var{Goal}
         ),
         @var{DB0}, @var{DB}).
 
@@ -5316,23 +5353,21 @@
 
 @end example
 
-Modify tuples for which @samp{@var{Goal}} or @samp{@var{Closure}}.
+Modify tuples for which @samp{@var{Goal}} or @samp{@var{Closure}} succeeds.
 Tuples for which the modification goal fails are left unchanged.
-There must be a @w{@samp{:- pragma base_relation}} declaration for
- at w{@samp{@var{PredOrFunc} @var{Name}/@var{Arity}}}.
 The original tuple is given by the first set of arguments, the
 updated tuple is given by the second set.
 
 For the third alternative @samp{@var{PredOrFunc}} must be either @samp{pred}
 or @samp{func}.
 
-When updating a predicate with type declaration
+When modifying a predicate with type declaration
 @w{@samp{:- pred p(aditi__state, @var{Type1}, @dots{})}}, @samp{@var{Closure}}
 must have type
 @samp{aditi_top_down pred(aditi__state, @var{Type1}, @dots{}, aditi__state, @var{Type1}, @dots{})},
 and inst @w{@samp{pred(unused, in, @dots{}, unused, out, @dots{}) is semidet}}.
 
-When updating a function with type declaration
+When modifying a function with type declaration
 @w{@samp{:- func p(aditi__state, @var{Type1}, @dots{}) = @var{Type2}}},
 @samp{@var{Closure}} must have type
 @samp{aditi_top_down pred(aditi__state, @var{Type1}, @dots{}, @var{Type2}, aditi__state, @var{Type1}, @dots{}, @var{Type2})},
@@ -5340,7 +5375,7 @@
 @w{@samp{pred(unused, in, @dots{}, in, unused, out, @dots{}, out) is semidet}}.
 
 The @samp{aditi__state} arguments of @samp{@var{Closure}} must have
-mode @samp{unused} -- it is not possible to call an Aditi
+mode @samp{unused} --- it is not possible to call an Aditi
 relation from the modification goal.
 
 If the construction of the lambda expression is in the same conjunction
@@ -5349,28 +5384,45 @@
 
 Examples:
 @example
+modify_example_1(DB0, DB) :-
         aditi_modify(
                 (p(_DB0, X, Y0) ==> p(_DB, X, Y) :-
                         X > 2, X < 5, Y = Y0 + 1
                 ), DB0, DB).
 
+modify_example_2(DB0, DB) :-
         aditi_modify(
-                ((q(_DB0, X) = Y0) ==> (q(_DB, X) = Y) :-
+                ((f(_DB0, X) = Y0) ==> (f(_DB, X) = Y) :-
                         X > 2, X < 5, Y = Y0 + 1
                 ), DB0, DB).
 
+modify_example_3(DB0, DB) :-
         ModifyP = (aditi_top_down pred(_::unused, X::in, Y0::in,
                         _::unused, X::out, Y::out) is semidet :-
                     X > 2, X < 5, Y = Y0 + 1
                  ),
         aditi_modify(pred p/3, ModifyP, DB0, DB).
 
+modify_example_4(DB0, DB) :-
         ModifyQ = (aditi_top_down pred(_::unused, X::in, Y0::in,
                         _::unused, X::out, Y::out) is semidet :-
                     X > 2, X < 5, Y = Y0 + 1
                  ),
-        aditi_modify(func q/2, ModifyQ, DB0, DB).
+        aditi_modify(func f/2, ModifyQ, DB0, DB).
+
+modify_example_5 -->
+        aditi_modify(
+                (p(_DB0, X, Y0) ==> p(_DB, X, Y) :-
+                        X > 2, X < 5, Y = Y0 + 1
+                )).
 @end example
+
+Note that in @samp{modify_example_5} the extra set of parentheses around
+the goal are needed, otherwise the second and third goals in
+the conjunction in the modification goal are parsed as arguments
+of the `aditi_modify' call. This behaviour is inconsistent with
+ISO Prolog syntax. An ISO Prolog implementation would report a
+syntax error without the extra set of parentheses.
 
 @node Aditi glossary
 @subsubsection Aditi glossary
--------------------------------------------------------------------------
mercury-developers mailing list
Post messages to:       mercury-developers at cs.mu.oz.au
Administrative Queries: owner-mercury-developers at cs.mu.oz.au
Subscriptions:          mercury-developers-request at cs.mu.oz.au
--------------------------------------------------------------------------



More information about the developers mailing list