[Mulgara-svn] r1393 - branches/xa11/src/jar/tuples/java/org/mulgara/store/tuples
pag at mulgara.org
pag at mulgara.org
Wed Dec 3 00:42:43 UTC 2008
Author: pag
Date: 2008-12-02 16:42:41 -0800 (Tue, 02 Dec 2008)
New Revision: 1393
Modified:
branches/xa11/src/jar/tuples/java/org/mulgara/store/tuples/TuplesOperations.java
Log:
Updated formatting for vertical whitespace
Modified: branches/xa11/src/jar/tuples/java/org/mulgara/store/tuples/TuplesOperations.java
===================================================================
--- branches/xa11/src/jar/tuples/java/org/mulgara/store/tuples/TuplesOperations.java 2008-12-03 00:00:56 UTC (rev 1392)
+++ branches/xa11/src/jar/tuples/java/org/mulgara/store/tuples/TuplesOperations.java 2008-12-03 00:42:41 UTC (rev 1393)
@@ -37,9 +37,7 @@
// Local packages
import org.mulgara.query.*;
-import org.mulgara.query.filter.And;
import org.mulgara.query.filter.Filter;
-import org.mulgara.query.filter.value.Bool;
import org.mulgara.resolver.spi.*;
import org.mulgara.util.StackTrace;
@@ -48,33 +46,17 @@
* {@link Variable}s to {@link Value}s.
*
* @created 2003-01-30
- *
* @author <a href="http://staff.pisoftware.com/raboczi">Simon Raboczi</a>
- *
- * @version $Revision: 1.12 $
- *
- * @modified $Date: 2005/05/16 11:07:10 $
- *
- * @maintenanceAuthor $Author: amuys $
- *
* @company <A href="mailto:info at PIsoftware.com">Plugged In Software</A>
- *
- * @copyright © 2003 <A href="http://www.PIsoftware.com/">Plugged In
- * Software Pty Ltd</A>
- *
+ * @copyright © 2003 <A href="http://www.PIsoftware.com/">Plugged In Software Pty Ltd</A>
* @licence <a href="{@docRoot}/../../LICENCE">Mozilla Public License v1.1</a>
*/
public abstract class TuplesOperations {
- /**
- * Logger. This is named after the class.
- */
- private final static Logger logger =
- Logger.getLogger(TuplesOperations.class.getName());
+ /** Logger. This is named after the class. */
+ private final static Logger logger = Logger.getLogger(TuplesOperations.class.getName());
- /**
- * The factory used to generate new {@link Tuples} instances.
- */
+ /** The factory used to generate new {@link Tuples} instances. */
private static TuplesFactory tuplesFactory = TuplesFactory.newInstance();
/**
@@ -84,10 +66,9 @@
* value to a tuples generates an empty result.
*
* @return the expression which is never satisfied, no matter what value any
- * variable takes
+ * variable takes
*/
public static StoreTuples empty() {
-
return EmptyTuples.getInstance();
}
@@ -103,7 +84,6 @@
* @return the expression which is always true, for any value of any variables
*/
public static StoreTuples unconstrained() {
-
return UnconstrainedTuples.getInstance();
}
@@ -111,12 +91,11 @@
* Assign a value to a variable, representing the binding as a tuples with one
* row and one column.
*
- * @param variable PARAMETER TO DO
- * @param value PARAMETER TO DO
- * @return RETURNED VALUE TO DO
+ * @param variable The variable to bind
+ * @param value The value in local space to bind the variable to
+ * @return A Tuples with the variable bound to the given value.
*/
public static Tuples assign(Variable variable, long value) {
-
return (value == Tuples.UNBOUND) ? (Tuples)unconstrained()
: new Assignment(variable, value);
}
@@ -124,9 +103,9 @@
/**
* This is approximately a disjunction.
*
- * @param lhs PARAMETER TO DO
- * @param rhs PARAMETER TO DO
- * @return RETURNED VALUE TO DO
+ * @param lhs The first Tuples to be used in the result.
+ * @param rhs The second Tuples to be used in the result.
+ * @return A new Tuples containing all of the bindings from the lhs and rhs parameters.
* @throws TuplesException if the append fails
*/
public static Tuples append(Tuples lhs, Tuples rhs) throws TuplesException {
@@ -134,40 +113,39 @@
}
- public static Tuples append(List args) throws TuplesException {
- if (logger.isDebugEnabled()) {
- logger.debug("Appending " + args);
- }
+ /**
+ * Creates a new Tuples which contains all of the bindings of the Tuples in the argument list.
+ * If any tuples contains variables not found in the other Tuples, then those values will
+ * remain unbound for the bindings of those Tuples missing those variables.
+ * @param args A list of the Tuples to be used in the result.
+ * @return A Tuples containing all of the bindings from the args list.
+ * @throws TuplesException If the data could not be appended.
+ */
+ public static Tuples append(List<? extends Tuples> args) throws TuplesException {
+ if (logger.isDebugEnabled()) logger.debug("Appending " + args);
- HashSet variableSet = new HashSet();
- List variables = new ArrayList();
+ HashSet<Variable> variableSet = new HashSet<Variable>();
+ List<Variable> variables = new ArrayList<Variable>();
boolean unionCompat = true;
Variable[] leftVars = null;
- List operands = new ArrayList();
- Iterator i = args.iterator();
+ List<Tuples> operands = new ArrayList<Tuples>();
+ Iterator<? extends Tuples> i = args.iterator();
while (i.hasNext()) {
- Tuples operand = (Tuples)i.next();
+ Tuples operand = i.next();
if (operand.isUnconstrained()) {
closeOperands(operands);
- if (logger.isDebugEnabled()) {
- logger.debug("Returning unconstrained from append.");
- }
+ if (logger.isDebugEnabled()) logger.debug("Returning unconstrained from append.");
return unconstrained();
} else if (operand.getRowCardinality() == Cursor.ZERO) {
- if (logger.isDebugEnabled()) {
- logger.debug("Ignoring append operand " + operand + " with rowcount = " + operand.getRowCount());
- }
+ if (logger.isDebugEnabled()) logger.debug("Ignoring append operand " + operand + " with rowcount = " + operand.getRowCount());
continue;
}
- operands.add(operand.clone());
+ operands.add((Tuples)operand.clone());
Variable[] vars = operand.getVariables();
- if (leftVars == null) {
- leftVars = vars;
- } else {
- unionCompat = unionCompat && Arrays.equals(leftVars, vars);
- }
+ if (leftVars == null) leftVars = vars;
+ else unionCompat = unionCompat && Arrays.equals(leftVars, vars);
for (int j = 0; j < vars.length; j++) {
if (!variableSet.contains(vars[j])) {
variableSet.add(vars[j]);
@@ -176,22 +154,16 @@
}
}
- if (logger.isDebugEnabled()) {
- logger.debug("Operands after append-unification: " + operands);
- }
+ if (logger.isDebugEnabled()) logger.debug("Operands after append-unification: " + operands);
if (operands.isEmpty()) {
- if (logger.isDebugEnabled()) {
- logger.debug("Returning empty from append.");
- }
+ if (logger.isDebugEnabled()) logger.debug("Returning empty from append.");
return empty();
}
if (operands.size() == 1) {
- if (logger.isDebugEnabled()) {
- logger.debug("Returning singleton from append.");
- }
- return (Tuples)operands.get(0);
+ if (logger.isDebugEnabled()) logger.debug("Returning singleton from append.");
+ return operands.get(0);
}
if (unionCompat) {
@@ -199,14 +171,12 @@
logger.debug("Columns are union-compatible");
logger.debug("Returning OrderedAppend from Union compatible append.");
}
- Tuples result = new OrderedAppend((Tuples[])operands.toArray(new Tuples[0]));
+ Tuples result = new OrderedAppend(operands.toArray(new Tuples[operands.size()]));
closeOperands(operands);
return result;
} else {
- List projected = new ArrayList();
- i = operands.iterator();
- while (i.hasNext()) {
- Tuples operand = (Tuples)i.next();
+ List<Tuples> projected = new ArrayList<Tuples>();
+ for (Tuples operand: operands) {
Tuples proj = project(operand, variables);
Tuples sorted = sort(proj);
projected.add(sorted);
@@ -214,10 +184,8 @@
operand.close();
}
- if (logger.isDebugEnabled()) {
- logger.debug("Returning OrderedAppend from Non-Union compatible append.");
- }
- Tuples result = new OrderedAppend((Tuples[])projected.toArray(new Tuples[0]));
+ if (logger.isDebugEnabled()) logger.debug("Returning OrderedAppend from Non-Union compatible append.");
+ Tuples result = new OrderedAppend(projected.toArray(new Tuples[projected.size()]));
closeOperands(projected);
return result;
}
@@ -225,50 +193,46 @@
/**
- * This is approximately a conjunction.
+ * Convenience method for doing a binary {@link #join(List)}.
+ * @param lhs The first argument to be joined.
+ * @param rhs The second argument to be joined.
+ * @return A Tuples containing the conjunction of lhs and rhs.
*/
public static Tuples join(Tuples lhs, Tuples rhs) throws TuplesException {
return join(Arrays.asList(new Tuples[] { lhs, rhs }));
}
- public static Tuples join(List args) throws TuplesException {
+ /**
+ * This is approximately a conjunction. Returns a set of bindings containing all the variables
+ * from both parameters. The only bindings returned are those where all the matching variables
+ * in each argument are bound to the same values.
+ * @param args The Tuples to be joined together.
+ * @return A Tuples containing the conjunction of all the arguments.
+ */
+ public static Tuples join(List<? extends Tuples> args) throws TuplesException {
try {
- if (logger.isDebugEnabled()) {
- logger.debug(printArgs("Flattening args:", args));
- }
- List operands = flattenOperands(args);
+ if (logger.isDebugEnabled()) logger.debug(printArgs("Flattening args:", args));
+ List<Tuples> operands = flattenOperands(args);
- if (logger.isDebugEnabled()) {
- logger.debug(printArgs("Unifying args: ", operands));
- }
- List unified = unifyOperands(operands);
+ if (logger.isDebugEnabled()) logger.debug(printArgs("Unifying args: ", operands));
+ List<Tuples> unified = unifyOperands(operands);
- if (logger.isDebugEnabled()) {
- logger.debug(printArgs("Sorting args:", unified));
- }
- List sorted = sortOperands(unified);
+ if (logger.isDebugEnabled()) logger.debug(printArgs("Sorting args:", unified));
+ List<Tuples> sorted = sortOperands(unified);
- if (logger.isDebugEnabled()) {
- logger.debug(printArgs("Preparing result: ", sorted));
- }
+ if (logger.isDebugEnabled()) logger.debug(printArgs("Preparing result: ", sorted));
switch (sorted.size()) {
case 0:
- if (logger.isDebugEnabled()) {
- logger.debug("Short-circuit empty");
- }
+ if (logger.isDebugEnabled()) logger.debug("Short-circuit empty");
return empty();
case 1:
- if (logger.isDebugEnabled()) {
- logger.debug("Short-circuit singleton");
- }
- return (Tuples)sorted.get(0);
+ if (logger.isDebugEnabled()) logger.debug("Short-circuit singleton");
+ return sorted.get(0);
default:
- if (logger.isDebugEnabled()) {
- logger.debug("return UnboundJoin");
- }
- Tuples result = new UnboundJoin((Tuples[]) sorted.toArray(new Tuples[0]));
+ if (logger.isDebugEnabled()) logger.debug("return UnboundJoin");
+ Tuples result = new UnboundJoin(sorted.toArray(new Tuples[sorted.size()]));
closeOperands(sorted);
return result;
}
@@ -293,12 +257,9 @@
*/
public static Tuples subtract(Tuples minuend, Tuples subtrahend) throws TuplesException {
try {
-
- if (logger.isDebugEnabled()) {
- logger.debug("subtracting " + subtrahend + " from " + minuend);
- }
+ if (logger.isDebugEnabled()) logger.debug("subtracting " + subtrahend + " from " + minuend);
// get the matching columns
- Set matchingVars = getMatchingVars(minuend, subtrahend);
+ Set<Variable> matchingVars = getMatchingVars(minuend, subtrahend);
if (matchingVars.isEmpty()) {
// check to see if the subtrahend is empty
if (subtrahend.getVariables().length == 0 || minuend.getVariables().length == 0) {
@@ -318,7 +279,7 @@
// yes, there are extra variables
logger.debug("removing extra variables not needed in subtraction");
// project out the extra variables (sorting happens in projection)
- sortedSubtrahend = project(subtrahend, new ArrayList(matchingVars));
+ sortedSubtrahend = project(subtrahend, new ArrayList<Variable>(matchingVars));
} else {
// there were no extra variables in the subtrahend
logger.debug("All variables needed");
@@ -329,9 +290,7 @@
try {
return new Difference(minuend, sortedSubtrahend);
} finally {
- if (sortedSubtrahend != subtrahend) {
- sortedSubtrahend.close();
- }
+ if (sortedSubtrahend != subtrahend) sortedSubtrahend.close();
}
} catch (RuntimeException re) {
@@ -357,9 +316,7 @@
public static Tuples optionalJoin(Tuples standard, Tuples optional, Filter filter, QueryEvaluationContext context) throws TuplesException {
try {
- if (logger.isDebugEnabled()) {
- logger.debug("optional join of " + standard + " optional { " + optional + " }");
- }
+ if (logger.isDebugEnabled()) logger.debug("optional join of " + standard + " optional { " + optional + " }");
// get the matching columns
Set<Variable> matchingVars = getMatchingVars(standard, optional);
@@ -389,9 +346,7 @@
}
// yes, there are extra variables
- if (logger.isDebugEnabled()) {
- logger.debug("sorting on the common variables: " + matchingVars);
- }
+ if (logger.isDebugEnabled()) logger.debug("sorting on the common variables: " + matchingVars);
// re-sort the optional according to the matching variables
// reorder the optional as necessary
Tuples sortedOptional = reSort(optional, new ArrayList<Variable>(matchingVars));
@@ -415,29 +370,29 @@
/**
* Flattens any nested joins to allow polyadic join operations.
+ * @param A list of Tuples which may in turn be nested operations.
+ * @return A flattened list of flattened Tuples.
*/
- private static List flattenOperands(List operands) throws TuplesException {
- List result = new ArrayList();
- Iterator i = operands.iterator();
- while (i.hasNext()) {
- result.addAll(flattenOperand((Tuples)i.next()));
- }
-
+ private static List<Tuples> flattenOperands(List<? extends Tuples> operands) throws TuplesException {
+ List<Tuples> result = new ArrayList<Tuples>();
+ for (Tuples operand: operands) result.addAll(flattenOperand(operand));
return result;
}
- private static List flattenOperand(Tuples operand) throws TuplesException {
- List operands = new ArrayList();
+ /**
+ * Flattens a Tuples into a list of Tuples. This means that joins will be expanded into their components.
+ * @param operand The Tuples to flatten
+ * @return A flattened list.
+ * @throws TuplesException If the Tuples could not be accessed.
+ */
+ private static List<Tuples> flattenOperand(Tuples operand) throws TuplesException {
+ List<Tuples> operands = new ArrayList<Tuples>();
if (operand instanceof UnboundJoin) {
- Iterator i = operand.getOperands().iterator();
- while (i.hasNext()) {
- operands.add(((Tuples)i.next()).clone());
- }
+ for (Tuples op: operand.getOperands()) operands.add((Tuples)op.clone());
} else {
- operands.add(operand.clone());
+ operands.add((Tuples)operand.clone());
}
-
return operands;
}
@@ -446,22 +401,22 @@
* Unifies bound variables in operands.
* Prepends a LiteralTuples containing constrained variable bindings.
* If any operand returns 0-rows returns EmptyTuples.
- *
* @param operands List of Tuples to unify. Consumed by this function.
* @return List of operands remaining after full unification.
*/
- private static List unifyOperands(List operands) throws TuplesException {
- Map bindings = new HashMap();
+ private static List<Tuples> unifyOperands(List<Tuples> operands) throws TuplesException {
+ Map<Variable,Long> bindings = new HashMap<Variable,Long>();
if (!bindSingleRowOperands(bindings, operands)) {
closeOperands(operands);
logger.debug("Returning empty due to shortcircuiting initial bindSingleRowOperands");
- return new ArrayList(Collections.singletonList(empty()));
+ return new ArrayList<Tuples>(Collections.singletonList(empty()));
}
- List result = extractNonReresolvableTuples(operands);
+ List<Tuples> result = extractNonReresolvableTuples(operands);
+ // operands is now effectively a List<ReresolvableResolution>
- List reresolved;
+ List<ReresolvableResolution> reresolved;
do {
reresolved = resolveNewlyBoundFreeNames(operands, bindings);
if (!bindSingleRowOperands(bindings, reresolved)) {
@@ -469,7 +424,8 @@
closeOperands(result);
closeOperands(reresolved);
logger.debug("Returning empty due to shortcircuiting progressive bindSingleRowOperands");
- return new ArrayList(Collections.singletonList(empty()));
+ // wrap in an Array list to convert the generic type
+ return new ArrayList<Tuples>(Collections.singletonList(empty()));
}
operands.addAll(reresolved);
} while (reresolved.size() != 0);
@@ -484,11 +440,10 @@
/**
* Extracts all bound names from workingSet into bindings.
*/
- private static boolean bindSingleRowOperands(Map bindings, List workingSet)
- throws TuplesException {
- Iterator iter = workingSet.iterator();
+ private static boolean bindSingleRowOperands(Map<Variable,Long> bindings, List<? extends Tuples> workingSet) throws TuplesException {
+ Iterator<? extends Tuples> iter = workingSet.iterator();
while (iter.hasNext()) {
- Tuples tuples = (Tuples)iter.next();
+ Tuples tuples = iter.next();
switch ((int)tuples.getRowCardinality()) {
case Cursor.ZERO:
@@ -501,22 +456,15 @@
for (int i = 0; i < vars.length; i++) {
Long value = new Long(tuples.getColumnValue(tuples.getColumnIndex(vars[i])));
Long oldValue = (Long)bindings.put(vars[i], value);
- if (oldValue != null && !value.equals(oldValue)) {
- return false;
- }
+ if (oldValue != null && !value.equals(oldValue)) return false;
}
} else {
// This should not happen.
// If the call to getRowCardinality returns > 0 then beforeFirst,
// and then next should return true too.
- logger.error(
- "No rows but getRowCardinality returned Cursor.ONE: (class=" +
- tuples.getClass().getName() + ") " + tuples.toString() + "\n" +
- new StackTrace()
- );
- throw new AssertionError(
- "No rows but getRowCardinality returned Cursor.ONE"
- );
+ logger.error("No rows but getRowCardinality returned Cursor.ONE: (class=" +
+ tuples.getClass().getName() + ") " + tuples.toString() + "\n" + new StackTrace());
+ throw new AssertionError("No rows but getRowCardinality returned Cursor.ONE");
}
iter.remove();
tuples.close();
@@ -534,13 +482,12 @@
}
- private static List extractNonReresolvableTuples(List workingSet)
- throws TuplesException {
- List nonReresolvable = new ArrayList(workingSet.size());
+ private static List<Tuples> extractNonReresolvableTuples(List<Tuples> workingSet) throws TuplesException {
+ List<Tuples> nonReresolvable = new ArrayList<Tuples>(workingSet.size());
- Iterator iter = workingSet.iterator();
+ Iterator<Tuples> iter = workingSet.iterator();
while (iter.hasNext()) {
- Tuples operand = (Tuples)iter.next();
+ Tuples operand = iter.next();
if (!(operand instanceof ReresolvableResolution)) {
nonReresolvable.add(operand);
iter.remove();
@@ -554,14 +501,14 @@
/**
* Compares the free names in the working-set against the current bindings
* and resolves any constraints found with bindings.
+ * @param workingSet A set of ReresolvableResolution, though it will be represented as a set of Tuples
* @return List of ConstrainedTuples resulting from any resolutions required.
*/
- private static List resolveNewlyBoundFreeNames(List workingSet, Map bindings)
- throws TuplesException {
- List reresolved = new ArrayList();
- Iterator iter = workingSet.iterator();
+ private static List<ReresolvableResolution> resolveNewlyBoundFreeNames(List<Tuples> workingSet, Map<Variable,Long> bindings) throws TuplesException {
+ List<ReresolvableResolution> reresolved = new ArrayList<ReresolvableResolution>();
+ Iterator<Tuples> iter = workingSet.iterator();
while (iter.hasNext()) {
- ReresolvableResolution tuples = (ReresolvableResolution) iter.next();
+ ReresolvableResolution tuples = (ReresolvableResolution)iter.next();
ReresolvableResolution updated = tuples.reresolve(bindings);
if (updated != null) {
reresolved.add(updated);
@@ -574,18 +521,14 @@
}
- private static Tuples createTuplesFromBindings(Map bindings)
- throws TuplesException {
- if (bindings.isEmpty()) {
- return unconstrained();
- }
+ private static Tuples createTuplesFromBindings(Map<Variable,Long> bindings) throws TuplesException {
+ if (bindings.isEmpty()) return unconstrained();
- Variable[] vars = (Variable[])bindings.keySet().toArray(new Variable[0]);
+ Set<Variable> keys = bindings.keySet();
+ Variable[] vars = keys.toArray(new Variable[keys.size()]);
long[] values = new long[vars.length];
- for (int i = 0; i < values.length; i++) {
- values[i] = ((Long)bindings.get(vars[i])).longValue();
- }
+ for (int i = 0; i < values.length; i++) values[i] = bindings.get(vars[i]);
LiteralTuples tuples = new LiteralTuples(vars);
tuples.appendTuple(values);
@@ -597,11 +540,8 @@
/**
* Calls close on all tuples in operands list.
*/
- private static void closeOperands(List operands) throws TuplesException {
- Iterator i = operands.iterator();
- while (i.hasNext()) {
- ((Tuples)i.next()).close();
- }
+ private static void closeOperands(List<? extends Tuples> operands) throws TuplesException {
+ for (Tuples op: operands) op.close();
}
@@ -610,18 +550,16 @@
* Each row count is discounted by the number of free-names bound to its left.
* Weighted-row-count = row-count ^ (free-after-binding / free-before-binding)
*/
- private static List sortOperands(List operands) throws TuplesException {
- Set boundVars = new HashSet();
- List result = new ArrayList();
+ private static List<Tuples> sortOperands(List<Tuples> operands) throws TuplesException {
+ Set<Variable> boundVars = new HashSet<Variable>();
+ List<Tuples> result = new ArrayList<Tuples>();
while (!operands.isEmpty()) {
Tuples bestTuples = removeBestTuples(operands, boundVars);
DefinablePrefixAnnotation definable =
(DefinablePrefixAnnotation)bestTuples.getAnnotation(DefinablePrefixAnnotation.class);
- if (definable != null) {
- definable.definePrefix(boundVars);
- }
+ if (definable != null) definable.definePrefix(boundVars);
// Add all variables that don't contain UNBOUND to boundVars set.
// Note: the inefficiency this introduces for distributed results
@@ -631,9 +569,7 @@
// left-operand it becomes unprefixed.
Variable[] vars = bestTuples.getVariables();
for (int i = 0; i < vars.length; i++) {
- if (!bestTuples.isColumnEverUnbound(i)) {
- boundVars.add(vars[i]);
- }
+ if (!bestTuples.isColumnEverUnbound(i)) boundVars.add(vars[i]);
}
result.add(bestTuples);
@@ -644,9 +580,8 @@
// FIXME: Method too long. Refactor.
- private static Tuples removeBestTuples(List operands, Set boundVars)
- throws TuplesException {
- ListIterator iter = operands.listIterator();
+ private static Tuples removeBestTuples(List<Tuples> operands, Set<Variable> boundVars) throws TuplesException {
+ ListIterator<Tuples> iter = operands.listIterator();
Tuples minTuples = null;
double minRowCount = Double.MAX_VALUE;
int minIndex = -1;
@@ -656,22 +591,17 @@
logger.debug("removeBestTuples");
while (iter.hasNext()) {
Tuples tuples = (Tuples)iter.next();
- if (logger.isDebugEnabled()) {
- logger.debug("tuples: " + tuplesSummary(tuples));
- }
+ if (logger.isDebugEnabled()) logger.debug("tuples: " + tuplesSummary(tuples));
// Check tuples meets any mandatory left bindings.
MandatoryBindingAnnotation bindingRequirements =
(MandatoryBindingAnnotation)tuples.getAnnotation(MandatoryBindingAnnotation.class);
- if (bindingRequirements != null && !bindingRequirements.meetsRequirement(boundVars)) {
- continue;
- }
+ if (bindingRequirements != null && !bindingRequirements.meetsRequirement(boundVars)) continue;
+
Variable[] vars = tuples.getVariables();
int numLeftBindings = calculateNumberOfLeftBindings(tuples, boundVars);
- if (logger.isDebugEnabled()) {
- logger.debug("numLeftBindings: " + numLeftBindings);
- }
+ if (logger.isDebugEnabled()) logger.debug("numLeftBindings: " + numLeftBindings);
// Basic formula assumes uniform distribution. So number of rows is the
// product of the length of each variable taken seperately, hence expected
@@ -703,39 +633,28 @@
if (minTuples == null) {
logger.info("Unable to meet ordering constraints with bindings: " + boundVars);
- Iterator i = operands.iterator();
- while (i.hasNext()) {
- logger.info(" Operand: " + tuplesSummary((Tuples)i.next()));
- }
+ for (Tuples op: operands) logger.info(" Operand: " + tuplesSummary(op));
throw new TuplesException("Unable to meet ordering constraints");
}
- if (logger.isDebugEnabled()) {
- logger.debug("Selected: " + tuplesSummary(minTuples) + " with weightedRowCount: " + minRowCount);
- }
+ if (logger.isDebugEnabled()) logger.debug("Selected: " + tuplesSummary(minTuples) + " with weightedRowCount: " + minRowCount);
operands.remove(minIndex);
return minTuples;
}
- private static int calculateNumberOfLeftBindings(Tuples tuples,
- Set boundVars) throws TuplesException {
+ private static int calculateNumberOfLeftBindings(Tuples tuples, Set<Variable> boundVars) throws TuplesException {
int numLeftBindings = 0;
Variable[] vars = tuples.getVariables();
// If the tuples supports defining a prefix then
if (tuples.getAnnotation(DefinablePrefixAnnotation.class) != null) {
for (int i = 0; i < vars.length; i++) {
- if (boundVars.contains(vars[i])) {
- numLeftBindings++;
- }
+ if (boundVars.contains(vars[i])) numLeftBindings++;
}
} else {
for (int i = 0; i < vars.length; i++) {
- if (boundVars.contains(vars[i])) {
- numLeftBindings++;
- } else {
- break;
- }
+ if (boundVars.contains(vars[i])) numLeftBindings++;
+ else break;
}
}
@@ -752,18 +671,14 @@
* @return RETURNED VALUE TO DO
* @throws TuplesException if the projection operation fails
*/
- public static Tuples project(Tuples tuples, List variableList)
- throws TuplesException {
+ public static Tuples project(Tuples tuples, List<Variable> variableList) throws TuplesException {
try {
boolean noVariables = (variableList == null) || (variableList.size() == 0);
- if (tuples.isUnconstrained() ||
- (noVariables && tuples.getRowCardinality() != Cursor.ZERO)) {
+ if (tuples.isUnconstrained() || (noVariables && tuples.getRowCardinality() != Cursor.ZERO)) {
- if (logger.isDebugEnabled()) {
- logger.debug("returning Unconstrained Tuples.");
- }
+ if (logger.isDebugEnabled()) logger.debug("returning Unconstrained Tuples.");
return TuplesOperations.unconstrained();
} else if (tuples.getRowCardinality() == Cursor.ZERO) {
@@ -773,9 +688,7 @@
} else if ((noVariables) && (tuples instanceof ConstrainedNegationTuples)) {
return empty();
} else {
- if (logger.isDebugEnabled()) {
- logger.debug("Projecting to " + variableList);
- }
+ if (logger.isDebugEnabled()) logger.debug("Projecting to " + variableList);
// Perform the actual projection
Tuples oldTuples = tuples;
@@ -792,12 +705,10 @@
oldTuples = tuples;
tuples = removeDuplicates(tuples);
assert tuples != oldTuples;
- if (tuples == oldTuples) {
- logger.warn("removeDuplicates does not change the underlying tuples");
- } else {
- oldTuples.close();
- }
+ if (tuples == oldTuples) logger.warn("removeDuplicates does not change the underlying tuples");
+ else oldTuples.close();
+
assert tuples.hasNoDuplicates();
return tuples;
@@ -808,6 +719,13 @@
}
+ /**
+ * Creates a new restriction tuples, based on a normal Tuples and a restriction predicate.
+ * @param tuples The tuples to restrict.
+ * @param pred The predicate describing the restriction.
+ * @return A new Tuples whose bindings only match the restriction.
+ * @throws TuplesException If the Tuples could not be accessed.
+ */
public static Tuples restrict(Tuples tuples, RestrictPredicate pred) throws TuplesException {
return new RestrictionTuples(tuples, pred);
}
@@ -830,9 +748,8 @@
/**
* Sort into default order, based on the columns and local node numbers.
- *
* @param tuples the tuples to sort
- * @return RETURNED VALUE TO DO
+ * @return A new Tuples with the bindings sorted.
* @throws TuplesException if the sorting can't be accomplished
*/
public static Tuples sort(Tuples tuples) throws TuplesException {
@@ -842,17 +759,13 @@
} else if (tuples.getRowCardinality() == Cursor.ZERO) {
tuples = empty();
} else {
- if (logger.isDebugEnabled()) {
- logger.debug("Sorting " + tuples.getRowCount() + " rows");
- }
+ if (logger.isDebugEnabled()) logger.debug("Sorting " + tuples.getRowCount() + " rows");
tuples = tuplesFactory.newTuples(tuples);
assert tuples.getComparator() != null;
}
- if (logger.isDebugEnabled()) {
- logger.debug("Sorted " + tuples.getRowCount() + " rows");
- }
+ if (logger.isDebugEnabled()) logger.debug("Sorted " + tuples.getRowCount() + " rows");
return tuples;
} else {
@@ -865,24 +778,15 @@
*
* @param tuples the tuples to sort
* @param rowComparator the ordering
- * @return RETURNED VALUE TO DO
+ * @return A Tuples with bindings sorted according to the rowComparator.
* @throws TuplesException if the sorting can't be accomplished
*/
- public static Tuples sort(Tuples tuples,
- RowComparator rowComparator) throws TuplesException {
-
+ public static Tuples sort(Tuples tuples, RowComparator rowComparator) throws TuplesException {
if (!rowComparator.equals(tuples.getComparator())) {
-
tuples = tuplesFactory.newTuples(tuples, rowComparator);
-
- if (logger.isDebugEnabled()) {
- logger.debug("Sorted: " + tuples + " (using supplied row comparator)");
- }
-
+ if (logger.isDebugEnabled()) logger.debug("Sorted: " + tuples + " (using supplied row comparator)");
return tuples;
- }
- else {
-
+ } else {
return (Tuples) tuples.clone();
}
}
@@ -963,10 +867,9 @@
* @param tuples the instance to limit
* @param rowCount the number of leading rows to retain
* @return the truncated tuples
- * @throws TuplesException EXCEPTION TO DO
+ * @throws TuplesException If there was an error accessing the Tuples.
*/
- public static Tuples limit(Tuples tuples, long rowCount)
- throws TuplesException {
+ public static Tuples limit(Tuples tuples, long rowCount) throws TuplesException {
return new LimitedTuples((Tuples) tuples.clone(), rowCount);
}
@@ -974,17 +877,13 @@
* If a tuples is virtual, evaluate and store it.
*
* @param tuples the instance to materialize
- * @return RETURNED VALUE TO DO
- * @throws TuplesException EXCEPTION TO DO
+ * @return A set of Tuples with any virtual bindings converted into actual bindings.
+ * @throws TuplesException If there was an error evaluating the virtual bindings
*/
public static Tuples materialize(Tuples tuples) throws TuplesException {
-
if (tuples.isMaterialized()) {
-
- return (Tuples) tuples.clone();
- }
- else {
-
+ return (Tuples)tuples.clone();
+ } else {
return tuplesFactory.newTuples(tuples);
}
}
@@ -998,32 +897,27 @@
* @param tuples the instance to offset
* @param rowCount the number of leading rows to remove
* @return the remaining rows, if any
- * @throws TuplesException EXCEPTION TO DO
+ * @throws TuplesException If there was an error accessing the tuples.
*/
- public static Tuples offset(Tuples tuples, long rowCount)
- throws TuplesException {
- return new OffsetTuples((Tuples) tuples.clone(), rowCount);
+ public static Tuples offset(Tuples tuples, long rowCount) throws TuplesException {
+ return new OffsetTuples((Tuples)tuples.clone(), rowCount);
}
/**
* Filter out duplicate rows.
*
- * @param tuples PARAMETER TO DO
- * @return RETURNED VALUE TO DO
- * @throws TuplesException EXCEPTION TO DO
+ * @param tuples The tuples to filter.
+ * @return An equivalent Tuples, but with duplicate bindings removed.
+ * @throws TuplesException If there was an error accessing the tuples.
*/
public static Tuples removeDuplicates(Tuples tuples) throws TuplesException {
if (tuples.hasNoDuplicates()) {
- if (logger.isDebugEnabled()) {
- logger.debug("Didn't need to remove duplicates");
- }
- return (Tuples) tuples.clone();
+ if (logger.isDebugEnabled()) logger.debug("Didn't need to remove duplicates");
+ return (Tuples)tuples.clone();
}
- if (logger.isDebugEnabled()) {
- logger.debug("Removing duplicates");
- }
+ if (logger.isDebugEnabled()) logger.debug("Removing duplicates");
if (tuples.getComparator() == null) {
Tuples oldTuples = tuples;
@@ -1039,12 +933,8 @@
}
return tuples;
- }
- else {
- if (logger.isDebugEnabled()) {
- logger.debug("Already sorted: " + tuples);
- }
-
+ } else {
+ if (logger.isDebugEnabled()) logger.debug("Already sorted: " + tuples);
Tuples result = new DistinctTuples(tuples);
return result;
}
@@ -1056,18 +946,16 @@
}
- public static StringBuffer tuplesSummary(Tuples tuples) {
- StringBuffer buff = new StringBuffer();
+ public static StringBuilder tuplesSummary(Tuples tuples) {
+ StringBuilder buff = new StringBuilder();
buff.append(tuples.getClass().toString());
buff.append("<" + System.identityHashCode(tuples) + ">");
buff.append("[");
- if (!tuples.isMaterialized()) {
- buff.append("~");
- } else {
- buff.append("=");
- }
+ if (!tuples.isMaterialized()) buff.append("~");
+ else buff.append("=");
+
try {
buff.append(tuples.getRowUpperBound()).append("]");
} catch (TuplesException et) {
@@ -1078,17 +966,13 @@
Variable[] vars = tuples.getVariables();
if (vars.length > 0) {
buff.append(vars[0].toString());
- for (int i = 1; i < vars.length; i++) {
- buff.append(", " + vars[i].toString());
- }
+ for (int i = 1; i < vars.length; i++) buff.append(", " + vars[i].toString());
}
buff.append("}");
try {
MandatoryBindingAnnotation mba = (MandatoryBindingAnnotation)tuples.getAnnotation(MandatoryBindingAnnotation.class);
- if (mba != null) {
- buff.append(" :: MBA{ " + mba.requiredVariables() + " }");
- }
+ if (mba != null) buff.append(" :: MBA{ " + mba.requiredVariables() + " }");
} catch (TuplesException et) {
logger.error("Failed to obtain annotation", et);
}
@@ -1127,90 +1011,40 @@
// get the variable list
Variable[] sv = tuples.getVariables();
for (int i = 0; i < sv.length; i++) {
- if (!vars.contains(sv[i])) {
- // extra variable
- return true;
- }
+ if (!vars.contains(sv[i])) return true; // extra variable
}
return false;
}
- private static String printArgs(String header, List args) {
- StringBuffer buff = new StringBuffer(header + "[");
- Iterator i = args.iterator();
- if (i.hasNext()) {
- buff.append(tuplesSummary((Tuples)i.next()));
+ /**
+ * Convert a list of Tuples into a string.
+ * @param header The header for the returned string.
+ * @param args The tuples to print.
+ * @return The string containing the full list of tuples.
+ */
+ private static String printArgs(String header, List<? extends Tuples> args) {
+ StringBuilder buff = new StringBuilder(header);
+ buff.append("[");
+ boolean first = true;
+ for (Tuples arg: args) {
+ if (!first) {
+ buff.append(", ");
+ first = false;
+ }
+ buff.append(tuplesSummary(arg));
}
-
- while (i.hasNext()) {
- buff.append(", " + tuplesSummary((Tuples)i.next()));
- }
buff.append("]");
return buff.toString();
}
- private static StringBuffer indentedTuplesTree(Tuples tuples, String indent) {
-
- StringBuffer buff = new StringBuffer();
-
+ private static StringBuilder indentedTuplesTree(Tuples tuples, String indent) {
+ StringBuilder buff = new StringBuilder();
buff.append("\n").append(indent).append("(").append(tuplesSummary(tuples));
-
- Iterator it = tuples.getOperands().iterator();
- while (it.hasNext()) {
- buff.append(" ").append(indentedTuplesTree((Tuples)it.next(), indent + ". "));
- }
-
+ for (Tuples t: tuples.getOperands()) buff.append(" ").append(indentedTuplesTree(t, indent + ". "));
buff.append(")");
-
return buff;
}
-
- /**
- * Count the number of leading columns and order has that are included in a
- * set variables.
- *
- * @param variableSet the set of variables
- * @param order the order
- * @return RETURNED VALUE TO DO
- */
- private static int leadingBindings(Tuples order, Set variableSet) {
-
- Variable[] variables = order.getVariables();
- int i = 0;
-
- while ( (i < variables.length) && variableSet.contains(variables[i])) {
-
- i++;
- }
-
- return i;
- }
-
- /**
- * Calculate projection orderings that allow indexed joins to function
- * optimally.
- *
- * @param self the tuples for which to generate a projection ordering
- * @param other the tuples the generated projection ordering should match
- * @return the projection ordering
- */
- private static List generateProjectionOrder(Tuples self, Tuples other) {
-
- // Calculate a new column ordering for self which moves all the columns
- // it has in common with the other into its prefix
- LinkedList selfColumns = new LinkedList(Arrays.asList(self.getVariables()));
- List otherColumns = Arrays.asList(other.getVariables());
-
- LinkedList suffix = new LinkedList(Arrays.asList(self.getVariables()));
- suffix.removeAll(otherColumns);
-
- selfColumns.retainAll(otherColumns);
- selfColumns.addAll(suffix);
-
- return selfColumns;
- }
-
}
More information about the Mulgara-svn
mailing list