Table mode declarations

By default, all the arguments of a tabled subgoal are used in variant checking and all answers are tabled for a tabled predicate. A table mode declaration allows the system to use only input arguments in variant checking and table answers selectively. The declaration
      :-table p(M1,...,Mn):C.
instructs the system how to do tabling on p/n, where C, called a cardinality limit, is an integer which limits the number of answers to be tabled, and Mi is a mode which can be min, max, + (input), or - (output). An argument with the mode min or max is assumed to be output. The system uses only input arguments in variant checking. If the cardinality limit C is 1, the declaration can be simply written as
      :-table p(M1,...,Mn).
For each predicate, only one declaration can be given.

An argument with the mode min or max is called an optimized or aggregate argument. In a tabled predicate, only one argument can be optimized, and the built-in @</2 is used to select answers with minimum or maximum values.



Examples:
Table modes are useful for declarative description of dynamic programming problems [6,20]. The following program encodes the Dijkstra's algorithm for finding a path with the minimum weight between a pair of nodes.

      :-table sp(+,+,-,min).
      sp(X,Y,[(X,Y)],W) :-
          edge(X,Y,W).
      sp(X,Y,[(X,Z)|Path],W) :-
          edge(X,Z,W1),
          sp(Z,Y,Path,W2),
          W is W1+W2.

The predicate edge(X,Y,W) defines a given weighted directed graph, where W is the weight of the edge from node X to node Y. The predicate sp(X,Y,Path,W) states that Path is a path from X to Y with the smallest weight W. Notice that whenever the predicate sp/4 is called, the first two arguments are always instantiated. So for each pair, only one answer is tabled.

Notice that if table modes are not respected or there is no bound for an optimized argument, a program may give unexpected answers. For example, if the weights of some edges are negative, there will be no lower bound for the optimized argument and hence the program will never stop.

Let's consider a variant of the problem which finds a shortest path among those with the minimum weight for each pair of nodes. The following gives a program:

      :-table sp(+,+,-,min).
      sp(X,Y,[(X,Y)],(W,1)) :-
          edge(X,Y,W).
      sp(X,Y,[(X,Z)|Path],(W,Len)) :-
          edge(X,Z,W1),
          sp(Z,Y,Path,(W2,Len1)),
          Len is Len1+1,
          W is W1+W2.

Since only one argument can be optimized, we use a compound term (W,Len) to denote the optimized valule where W is the weight and Len is the length of a path. Notice that the order is important. If the term were (Len,W), the program would find a shortest path, breaking tie by selecting one with the minimum weight.

The cardinality limit of a tabled predicate can be dynamically changed using the built-in table_cardinality_limit.

Neng-Fa Zhou 2012-01-03