Two-Column, Two-Table Example

[This is preliminary documentation and subject to change.]

Consider the following SELECT statement:

SELECT c1t1, c1t2 FROM t1,t2 

The SQLPrepare phase for this statement proceeds as before. Here, however, there are two columns, each from a separate table. The SELECT statement is asking for the Cartesian cross product of the columns in the tables. This differs from the single-column, single-table example in that, for each value of c1t1, the adapter must iterate over t2 (assuming the c1t1 spins fastest). Thus, for each c1t1, the adapter must reset the t2 enumeration and Next over the enumeration for all elements.

The behavior of an enumeration in each Next is unknown to the adapter. For example, one provider may get all the information it needs to return all row information when the enumeration is created. Another might only retrieve the information on a just-in-time basis. For example, when Next is invoked it gathers the information necessary to return the corresponding row information. Which strategy is employed is provider-dependent and depends on the static nature of the provided data. If the adapter is a dynamic instance provider, it may choose to get the data on a Next. In this case, if the adapter resets the enumeration and invokes Next again, the provider retrieves the data needed to build the row information to be returned.

There can be efficiency problems if there are many columns in the select list and many rows or instances per table. Further, during any particular invocation, the adapter expects the contents enumerated to remain the same. That is, the adapter really wants a snapshot of the enumerated instances when the execution is done. The adapter may have to do its own caching of row information as each enumeration is iterated through.

The next case adds a WHERE predicate to the select statement. Here is a straightforward restricted SELECT:

SELECT c1t1, c1t2 FROM t1, t2 WHERE  c2t1 = 10 

In this case, SQLPrepare builds a complete predicate tree that represents the WHERE clause. SQLPrepare also checks and annotates the semantics of this parse tree, much the same way that it checks the semantics of the select list.

SQLFetch accesses the instances of the classes in a rightmost, slowest manner as for the previous case. Here, however, the predicate tree is evaluated with the properties of the current instances to determine if the current combination of instances qualify for the resultant rowset.

See Also

ODBC Handles