提交 da10d540 authored 作者: Evgenij Ryazanov's avatar Evgenij Ryazanov

Add Expression.getSubexpression() and getSubexpressionCount()

上级 3fc4e02e
......@@ -12,19 +12,14 @@ import java.util.List;
import org.h2.api.ErrorCode;
import org.h2.command.Prepared;
import org.h2.engine.Database;
import org.h2.engine.Session;
import org.h2.engine.Mode.ModeEnum;
import org.h2.engine.Session;
import org.h2.expression.Alias;
import org.h2.expression.Comparison;
import org.h2.expression.ConditionAndOr;
import org.h2.expression.ConditionNot;
import org.h2.expression.Expression;
import org.h2.expression.ExpressionColumn;
import org.h2.expression.ExpressionVisitor;
import org.h2.expression.Function;
import org.h2.expression.Operation;
import org.h2.expression.Parameter;
import org.h2.expression.UnaryOperation;
import org.h2.expression.ValueExpression;
import org.h2.message.DbException;
import org.h2.result.ResultInterface;
......@@ -530,6 +525,7 @@ public abstract class Query extends Prepared {
*/
private static boolean checkOrderOther(Session session, Expression expr, ArrayList<String> expressionSQL) {
if (expr.isConstant()) {
// ValueExpression or other
return true;
}
String exprSQL = expr.getSQL();
......@@ -538,41 +534,19 @@ public abstract class Query extends Prepared {
return true;
}
}
if (expr instanceof Function) {
Function function = (Function) expr;
if (!function.isDeterministic()) {
int count = expr.getSubexpressionCount();
if (expr instanceof Function ? !((Function) expr).isDeterministic() : count <= 0) {
// If expression is a non-deterministic function or expression is an
// ExpressionColumn, Parameter, SequenceValue or has other
// unsupported type without subexpressions
return false;
}
for (int i = 0; i < count; i++) {
if (!checkOrderOther(session, expr.getSubexpression(i), expressionSQL)) {
return false;
}
for (Expression e : function.getArgs()) {
if (!checkOrderOther(session, e, expressionSQL)) {
return false;
}
}
return true;
}
if (expr instanceof Operation) {
Operation operation = (Operation) expr;
Expression right = operation.getRightSubExpression();
return checkOrderOther(session, operation.getLeftSubExpression(), expressionSQL)
&& (right == null || checkOrderOther(session, right, expressionSQL));
}
if (expr instanceof UnaryOperation) {
return checkOrderOther(session, ((UnaryOperation) expr).getSubExpression(), expressionSQL);
}
if (expr instanceof ConditionAndOr) {
ConditionAndOr condition = (ConditionAndOr) expr;
return checkOrderOther(session, condition.getLeftSubExpression(), expressionSQL)
&& checkOrderOther(session, condition.getRightSubExpression(), expressionSQL);
}
if (expr instanceof ConditionNot) {
return checkOrderOther(session, ((ConditionNot) expr).getSubCondition(), expressionSQL);
}
if (expr instanceof Comparison) {
Comparison condition = (Comparison) expr;
return checkOrderOther(session, condition.getLeftSubExpression(), expressionSQL)
&& checkOrderOther(session, condition.getRightSubExpression(), expressionSQL);
}
return false;
return true;
}
/**
......
......@@ -587,22 +587,24 @@ public class Comparison extends Condition {
return null;
}
/**
* Get the left sub-expression of this condition.
*
* @return the left sub-expression
*/
public Expression getLeftSubExpression() {
return left;
@Override
public int getSubexpressionCount() {
return compareType == IS_NULL || compareType == IS_NOT_NULL ? 1 : 2;
}
/**
* Get the right sub-expression of this condition.
*
* @return the right sub-expression
*/
public Expression getRightSubExpression() {
return right;
@Override
public Expression getSubexpression(int index) {
switch (index) {
case 0:
return left;
case 1:
if (compareType != IS_NULL && compareType != IS_NOT_NULL) {
return right;
}
//$FALL-THROUGH$
default:
throw new IndexOutOfBoundsException();
}
}
}
......@@ -283,22 +283,21 @@ public class ConditionAndOr extends Condition {
return left.getCost() + right.getCost();
}
/**
* Get the left sub-expression of this condition.
*
* @return the left sub-expression
*/
public Expression getLeftSubExpression() {
return left;
@Override
public int getSubexpressionCount() {
return 2;
}
/**
* Get the right sub-expression of this condition.
*
* @return the right sub-expression
*/
public Expression getRightSubExpression() {
return right;
@Override
public Expression getSubexpression(int index) {
switch (index) {
case 0:
return left;
case 1:
return right;
default:
throw new IndexOutOfBoundsException();
}
}
}
......@@ -98,13 +98,17 @@ public class ConditionNot extends Condition {
return condition.getCost();
}
/**
* Get the sub-expression of this condition.
*
* @return the sub-expression
*/
public Expression getSubCondition() {
return condition;
@Override
public int getSubexpressionCount() {
return 1;
}
@Override
public Expression getSubexpression(int index) {
if (index == 0) {
return condition;
}
throw new IndexOutOfBoundsException();
}
}
......@@ -357,4 +357,24 @@ public abstract class Expression {
}
}
/**
* Returns count of subexpressions.
*
* @return count of subexpressions
*/
public int getSubexpressionCount() {
return 0;
}
/**
* Returns subexpression with specified index.
*
* @param index 0-based index
* @return subexpression with specified index
* @throws IndexOutOfBoundsException if specified index is not valid
*/
public Expression getSubexpression(int index) {
throw new IndexOutOfBoundsException();
}
}
......@@ -2710,4 +2710,14 @@ public class Function extends Expression implements FunctionCall {
return info.type == NEXTVAL;
}
@Override
public int getSubexpressionCount() {
return args.length;
}
@Override
public Expression getSubexpression(int index) {
return args[index];
}
}
......@@ -451,22 +451,21 @@ public class Operation extends Expression {
return left.getCost() + right.getCost() + 1;
}
/**
* Get the left sub-expression of this operation.
*
* @return the left sub-expression
*/
public Expression getLeftSubExpression() {
return left;
@Override
public int getSubexpressionCount() {
return 2;
}
/**
* Get the right sub-expression of this operation.
*
* @return the right sub-expression
*/
public Expression getRightSubExpression() {
return right;
@Override
public Expression getSubexpression(int index) {
switch (index) {
case 0:
return left;
case 1:
return right;
default:
throw new IndexOutOfBoundsException();
}
}
}
......@@ -96,13 +96,17 @@ public class UnaryOperation extends Expression {
return arg.getCost() + 1;
}
/**
* Get the sub-expression of this operation.
*
* @return the sub-expression
*/
public Expression getSubExpression() {
return arg;
@Override
public int getSubexpressionCount() {
return 1;
}
@Override
public Expression getSubexpression(int index) {
if (index == 0) {
return arg;
}
throw new IndexOutOfBoundsException();
}
}
......@@ -669,19 +669,17 @@ public class FullText {
ArrayList<String> data, Expression expr) {
if (expr instanceof ConditionAndOr) {
ConditionAndOr and = (ConditionAndOr) expr;
Expression left = and.getLeftSubExpression();
Expression right = and.getRightSubExpression();
addColumnData(columns, data, left);
addColumnData(columns, data, right);
addColumnData(columns, data, and.getSubexpression(0));
addColumnData(columns, data, and.getSubexpression(1));
} else {
Comparison comp = (Comparison) expr;
ExpressionColumn ec = (ExpressionColumn) comp.getLeftSubExpression();
ValueExpression ev = (ValueExpression) comp.getRightSubExpression();
ExpressionColumn ec = (ExpressionColumn) comp.getSubexpression(0);
String columnName = ec.getColumnName();
columns.add(columnName);
if (ev == null) {
if (expr.getSubexpressionCount() == 1) {
data.add(null);
} else {
ValueExpression ev = (ValueExpression) comp.getSubexpression(1);
data.add(ev.getValue(null).getString());
}
}
......
......@@ -66,6 +66,9 @@ SELECT DISTINCT NAME, ID + 1 FROM TEST ORDER BY UPPER(NAME) || (ID + 1);
SELECT DISTINCT ID FROM TEST ORDER BY NAME;
> exception ORDER_BY_NOT_IN_RESULT
SELECT DISTINCT ID FROM TEST ORDER BY UPPER(NAME);
> exception ORDER_BY_NOT_IN_RESULT
SELECT DISTINCT ID FROM TEST ORDER BY CURRENT_TIMESTAMP;
> exception ORDER_BY_NOT_IN_RESULT
......
......@@ -789,4 +789,4 @@ inconsistencies discover eliminated violates tweaks postpone leftovers
tied ties
launched unavailable smallmoney erroneously multiplier newid pan streamline unmap preview unexpectedly presumably
converging smth rng curs casts unmapping unmapper
immediate hhmmss scheduled hhmm prematurely postponed arranges
immediate hhmmss scheduled hhmm prematurely postponed arranges subexpression subexpressions
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论