package net.sourceforge.mayfly.evaluation.select;
import net.sourceforge.mayfly.Options;
import net.sourceforge.mayfly.datastore.Cell;
import net.sourceforge.mayfly.datastore.DataStore;
import net.sourceforge.mayfly.datastore.TableData;
import net.sourceforge.mayfly.evaluation.Expression;
import net.sourceforge.mayfly.evaluation.ResultRow;
import net.sourceforge.mayfly.evaluation.expression.SingleColumn;
import net.sourceforge.mayfly.evaluation.from.FromTable;
import net.sourceforge.mayfly.parser.Location;
/**
@internal
This class is responsible for looking up names and also keeping a hold
of the store and current schema (I guess because the two tasks seemed
to need the same information).
Cases for evaluating a name are:
- column name, directly
- value from the outer query of a correlated subquery, for example
candidate.region in:
SELECT name FROM countries candidate
WHERE population >=
(SELECT max(population) FROM countries other
WHERE other.region = candidate.region)
- column alias (total in select a + b as total).
*/
public abstract class Evaluator {
public static final Evaluator NO_SUBSELECT_NEEDED =
new NoSubselectEvaluator();
abstract public DataStore store();
abstract public String currentSchema();
public Cell lookup(ResultRow row,
String tableOrAlias, String originalTableOrAlias, String columnName, Location location) {
Expression found = row.findColumn(
tableOrAlias, originalTableOrAlias, columnName, location);
return row.findValue(found);
}
public TableData table(FromTable table) {
return store().table(currentSchema(), table.tableName);
}
public Options options() {
return new Options();
}
/**
* @internal
* row is usually (always?) a dummy row. The concept we are
* heading towards, as with
* {@link Expression#resolve(ResultRow, Evaluator)}, is that resolving
* names is part of an optimization/planning phase which happens
* once, not once for every row.
*/
public Expression lookupName(ResultRow row, String name, Location location) {
SingleColumn found = row.findColumnOrNull(null, name, location);
if (found != null) {
return found.asResultOfResolution(name, location);
}
return null;
}
public final Expression lookupName(ResultRow row, String name) {
return lookupName(row, name, Location.UNKNOWN);
}
}