This is an automated email from the ASF dual-hosted git repository.
jackietien pushed a commit to branch ty/TableModelGrammar
in repository https://gitbox.apache.org/repos/asf/iotdb.git
The following commit(s) were added to refs/heads/ty/TableModelGrammar by this
push:
new cdc1fdd320f partial expression
cdc1fdd320f is described below
commit cdc1fdd320f6e67258290f05e15f100c363c7994
Author: JackieTien97 <[email protected]>
AuthorDate: Wed Feb 7 18:20:14 2024 +0800
partial expression
---
.../db/relational/grammar/sql/RelationalSql.g4 | 1 -
.../iotdb/db/relational/sql/parser/AstBuilder.java | 1042 ++++++++++++++++++++
.../iotdb/db/relational/sql/tree/AllRows.java | 67 ++
.../sql/tree/ArithmeticBinaryExpression.java | 119 +++
.../sql/tree/ArithmeticUnaryExpression.java | 114 +++
.../iotdb/db/relational/sql/tree/AstVisitor.java | 404 ++++++++
.../db/relational/sql/tree/BetweenPredicate.java | 106 ++
.../apache/iotdb/db/relational/sql/tree/Cast.java | 133 +++
.../db/relational/sql/tree/CoalesceExpression.java | 92 ++
.../relational/sql/tree/ComparisonExpression.java | 171 ++++
.../db/relational/sql/tree/CurrentDatabase.java | 70 ++
.../iotdb/db/relational/sql/tree/CurrentUser.java | 70 ++
.../sql/tree/{AstVisitor.java => DataType.java} | 14 +-
.../{AstVisitor.java => DataTypeParameter.java} | 15 +-
.../relational/sql/tree/DereferenceExpression.java | 151 +++
.../db/relational/sql/tree/DescribeTable.java | 80 ++
.../db/relational/sql/tree/ExistsPredicate.java | 80 ++
.../sql/tree/{AstVisitor.java => Expression.java} | 17 +-
.../db/relational/sql/tree/FieldReference.java | 80 ++
.../iotdb/db/relational/sql/tree/FunctionCall.java | 113 +++
.../db/relational/sql/tree/GenericDataType.java | 88 ++
.../iotdb/db/relational/sql/tree/Identifier.java | 138 +++
.../iotdb/db/relational/sql/tree/IfExpression.java | 105 ++
.../db/relational/sql/tree/InListExpression.java | 83 ++
.../iotdb/db/relational/sql/tree/InPredicate.java | 86 ++
.../sql/tree/{AstVisitor.java => Literal.java} | 19 +-
.../apache/iotdb/db/relational/sql/tree/Node.java | 2 +-
.../db/relational/sql/tree/NumericParameter.java | 88 ++
.../iotdb/db/relational/sql/tree/Property.java | 120 +++
.../db/relational/sql/tree/QualifiedName.java | 139 +++
.../db/relational/sql/tree/SetProperties.java | 107 ++
.../sql/tree/{AstVisitor.java => Statement.java} | 15 +-
.../sql/tree/{Node.java => TypeParameter.java} | 63 +-
.../apache/iotdb/db/relational/sql/tree/Use.java | 81 ++
.../relational/sql/util/ExpressionFormatter.java | 50 +
35 files changed, 4050 insertions(+), 73 deletions(-)
diff --git
a/iotdb-core/relational-grammar/src/main/antlr4/org/apache/iotdb/db/relational/grammar/sql/RelationalSql.g4
b/iotdb-core/relational-grammar/src/main/antlr4/org/apache/iotdb/db/relational/grammar/sql/RelationalSql.g4
index 490ece0393e..e67a6ffe7a5 100644
---
a/iotdb-core/relational-grammar/src/main/antlr4/org/apache/iotdb/db/relational/grammar/sql/RelationalSql.g4
+++
b/iotdb-core/relational-grammar/src/main/antlr4/org/apache/iotdb/db/relational/grammar/sql/RelationalSql.g4
@@ -533,7 +533,6 @@ predicate[ParserRuleContext value]
valueExpression
: primaryExpression
#valueExpressionDefault
- | valueExpression AT timeZoneSpecifier
#atTimeZone
| operator=(MINUS | PLUS) valueExpression
#arithmeticUnary
| left=valueExpression operator=(ASTERISK | SLASH | PERCENT)
right=valueExpression #arithmeticBinary
| left=valueExpression operator=(PLUS | MINUS) right=valueExpression
#arithmeticBinary
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/parser/AstBuilder.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/parser/AstBuilder.java
index 66654fdb83c..b40c49aded0 100644
---
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/parser/AstBuilder.java
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/parser/AstBuilder.java
@@ -20,6 +20,7 @@
package org.apache.iotdb.db.relational.sql.parser;
import org.apache.iotdb.db.relational.grammar.sql.RelationalSqlBaseVisitor;
+import org.apache.iotdb.db.relational.grammar.sql.RelationalSqlParser;
import org.apache.iotdb.db.relational.sql.tree.Node;
import org.apache.iotdb.db.relational.sql.tree.NodeLocation;
@@ -41,6 +42,1047 @@ public class AstBuilder extends
RelationalSqlBaseVisitor<Node> {
this.baseLocation = baseLocation;
}
+ @Override
+ public Node visitSingleStatement(RelationalSqlParser.SingleStatementContext
ctx) {
+ return visit(ctx.statement());
+ }
+
+ @Override
+ public Node
visitUseDatabaseStatement(RelationalSqlParser.UseDatabaseStatementContext ctx) {
+ return super.visitUseDatabaseStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowDatabasesStatement(RelationalSqlParser.ShowDatabasesStatementContext
ctx) {
+ return super.visitShowDatabasesStatement(ctx);
+ }
+
+ @Override
+ public Node
visitCreateDbStatement(RelationalSqlParser.CreateDbStatementContext ctx) {
+ return super.visitCreateDbStatement(ctx);
+ }
+
+ @Override
+ public Node visitDropDbStatement(RelationalSqlParser.DropDbStatementContext
ctx) {
+ return super.visitDropDbStatement(ctx);
+ }
+
+ @Override
+ public Node visitCharsetDesc(RelationalSqlParser.CharsetDescContext ctx) {
+ return super.visitCharsetDesc(ctx);
+ }
+
+ @Override
+ public Node
visitCreateTableStatement(RelationalSqlParser.CreateTableStatementContext ctx) {
+ return super.visitCreateTableStatement(ctx);
+ }
+
+ @Override
+ public Node
visitColumnDefinition(RelationalSqlParser.ColumnDefinitionContext ctx) {
+ return super.visitColumnDefinition(ctx);
+ }
+
+ @Override
+ public Node visitColumnCategory(RelationalSqlParser.ColumnCategoryContext
ctx) {
+ return super.visitColumnCategory(ctx);
+ }
+
+ @Override
+ public Node visitCharsetName(RelationalSqlParser.CharsetNameContext ctx) {
+ return super.visitCharsetName(ctx);
+ }
+
+ @Override
+ public Node
visitDropTableStatement(RelationalSqlParser.DropTableStatementContext ctx) {
+ return super.visitDropTableStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowTableStatement(RelationalSqlParser.ShowTableStatementContext ctx) {
+ return super.visitShowTableStatement(ctx);
+ }
+
+ @Override
+ public Node
visitDescTableStatement(RelationalSqlParser.DescTableStatementContext ctx) {
+ return super.visitDescTableStatement(ctx);
+ }
+
+ @Override
+ public Node visitRenameTable(RelationalSqlParser.RenameTableContext ctx) {
+ return super.visitRenameTable(ctx);
+ }
+
+ @Override
+ public Node visitAddColumn(RelationalSqlParser.AddColumnContext ctx) {
+ return super.visitAddColumn(ctx);
+ }
+
+ @Override
+ public Node visitRenameColumn(RelationalSqlParser.RenameColumnContext ctx) {
+ return super.visitRenameColumn(ctx);
+ }
+
+ @Override
+ public Node visitDropColumn(RelationalSqlParser.DropColumnContext ctx) {
+ return super.visitDropColumn(ctx);
+ }
+
+ @Override
+ public Node
visitSetTableProperties(RelationalSqlParser.SetTablePropertiesContext ctx) {
+ return super.visitSetTableProperties(ctx);
+ }
+
+ @Override
+ public Node
visitCreateIndexStatement(RelationalSqlParser.CreateIndexStatementContext ctx) {
+ return super.visitCreateIndexStatement(ctx);
+ }
+
+ @Override
+ public Node visitIdentifierList(RelationalSqlParser.IdentifierListContext
ctx) {
+ return super.visitIdentifierList(ctx);
+ }
+
+ @Override
+ public Node
visitDropIndexStatement(RelationalSqlParser.DropIndexStatementContext ctx) {
+ return super.visitDropIndexStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowIndexStatement(RelationalSqlParser.ShowIndexStatementContext ctx) {
+ return super.visitShowIndexStatement(ctx);
+ }
+
+ @Override
+ public Node visitInsertStatement(RelationalSqlParser.InsertStatementContext
ctx) {
+ return super.visitInsertStatement(ctx);
+ }
+
+ @Override
+ public Node visitDeleteStatement(RelationalSqlParser.DeleteStatementContext
ctx) {
+ return super.visitDeleteStatement(ctx);
+ }
+
+ @Override
+ public Node visitUpdateStatement(RelationalSqlParser.UpdateStatementContext
ctx) {
+ return super.visitUpdateStatement(ctx);
+ }
+
+ @Override
+ public Node
visitCreateFunctionStatement(RelationalSqlParser.CreateFunctionStatementContext
ctx) {
+ return super.visitCreateFunctionStatement(ctx);
+ }
+
+ @Override
+ public Node visitUriClause(RelationalSqlParser.UriClauseContext ctx) {
+ return super.visitUriClause(ctx);
+ }
+
+ @Override
+ public Node
visitDropFunctionStatement(RelationalSqlParser.DropFunctionStatementContext
ctx) {
+ return super.visitDropFunctionStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowFunctionsStatement(RelationalSqlParser.ShowFunctionsStatementContext
ctx) {
+ return super.visitShowFunctionsStatement(ctx);
+ }
+
+ @Override
+ public Node
visitLoadTsFileStatement(RelationalSqlParser.LoadTsFileStatementContext ctx) {
+ return super.visitLoadTsFileStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowDevicesStatement(RelationalSqlParser.ShowDevicesStatementContext ctx) {
+ return super.visitShowDevicesStatement(ctx);
+ }
+
+ @Override
+ public Node
visitCountDevicesStatement(RelationalSqlParser.CountDevicesStatementContext
ctx) {
+ return super.visitCountDevicesStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowClusterStatement(RelationalSqlParser.ShowClusterStatementContext ctx) {
+ return super.visitShowClusterStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowRegionsStatement(RelationalSqlParser.ShowRegionsStatementContext ctx) {
+ return super.visitShowRegionsStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowDataNodesStatement(RelationalSqlParser.ShowDataNodesStatementContext
ctx) {
+ return super.visitShowDataNodesStatement(ctx);
+ }
+
+ @Override
+ public Node visitShowConfigNodesStatement(
+ RelationalSqlParser.ShowConfigNodesStatementContext ctx) {
+ return super.visitShowConfigNodesStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowClusterIdStatement(RelationalSqlParser.ShowClusterIdStatementContext
ctx) {
+ return super.visitShowClusterIdStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowRegionIdStatement(RelationalSqlParser.ShowRegionIdStatementContext
ctx) {
+ return super.visitShowRegionIdStatement(ctx);
+ }
+
+ @Override
+ public Node visitShowTimeSlotListStatement(
+ RelationalSqlParser.ShowTimeSlotListStatementContext ctx) {
+ return super.visitShowTimeSlotListStatement(ctx);
+ }
+
+ @Override
+ public Node visitCountTimeSlotListStatement(
+ RelationalSqlParser.CountTimeSlotListStatementContext ctx) {
+ return super.visitCountTimeSlotListStatement(ctx);
+ }
+
+ @Override
+ public Node visitShowSeriesSlotListStatement(
+ RelationalSqlParser.ShowSeriesSlotListStatementContext ctx) {
+ return super.visitShowSeriesSlotListStatement(ctx);
+ }
+
+ @Override
+ public Node
visitMigrateRegionStatement(RelationalSqlParser.MigrateRegionStatementContext
ctx) {
+ return super.visitMigrateRegionStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowVariablesStatement(RelationalSqlParser.ShowVariablesStatementContext
ctx) {
+ return super.visitShowVariablesStatement(ctx);
+ }
+
+ @Override
+ public Node visitFlushStatement(RelationalSqlParser.FlushStatementContext
ctx) {
+ return super.visitFlushStatement(ctx);
+ }
+
+ @Override
+ public Node
visitClearCacheStatement(RelationalSqlParser.ClearCacheStatementContext ctx) {
+ return super.visitClearCacheStatement(ctx);
+ }
+
+ @Override
+ public Node
visitRepairDataStatement(RelationalSqlParser.RepairDataStatementContext ctx) {
+ return super.visitRepairDataStatement(ctx);
+ }
+
+ @Override
+ public Node visitSetSystemStatusStatement(
+ RelationalSqlParser.SetSystemStatusStatementContext ctx) {
+ return super.visitSetSystemStatusStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowVersionStatement(RelationalSqlParser.ShowVersionStatementContext ctx) {
+ return super.visitShowVersionStatement(ctx);
+ }
+
+ @Override
+ public Node
visitShowQueriesStatement(RelationalSqlParser.ShowQueriesStatementContext ctx) {
+ return super.visitShowQueriesStatement(ctx);
+ }
+
+ @Override
+ public Node
visitKillQueryStatement(RelationalSqlParser.KillQueryStatementContext ctx) {
+ return super.visitKillQueryStatement(ctx);
+ }
+
+ @Override
+ public Node visitLoadConfigurationStatement(
+ RelationalSqlParser.LoadConfigurationStatementContext ctx) {
+ return super.visitLoadConfigurationStatement(ctx);
+ }
+
+ @Override
+ public Node
visitLocalOrClusterMode(RelationalSqlParser.LocalOrClusterModeContext ctx) {
+ return super.visitLocalOrClusterMode(ctx);
+ }
+
+ @Override
+ public Node
visitStatementDefault(RelationalSqlParser.StatementDefaultContext ctx) {
+ return super.visitStatementDefault(ctx);
+ }
+
+ @Override
+ public Node visitExplain(RelationalSqlParser.ExplainContext ctx) {
+ return super.visitExplain(ctx);
+ }
+
+ @Override
+ public Node visitExplainAnalyze(RelationalSqlParser.ExplainAnalyzeContext
ctx) {
+ return super.visitExplainAnalyze(ctx);
+ }
+
+ @Override
+ public Node visitQuery(RelationalSqlParser.QueryContext ctx) {
+ return super.visitQuery(ctx);
+ }
+
+ @Override
+ public Node visitWith(RelationalSqlParser.WithContext ctx) {
+ return super.visitWith(ctx);
+ }
+
+ @Override
+ public Node visitProperties(RelationalSqlParser.PropertiesContext ctx) {
+ return super.visitProperties(ctx);
+ }
+
+ @Override
+ public Node
visitPropertyAssignments(RelationalSqlParser.PropertyAssignmentsContext ctx) {
+ return super.visitPropertyAssignments(ctx);
+ }
+
+ @Override
+ public Node visitProperty(RelationalSqlParser.PropertyContext ctx) {
+ return super.visitProperty(ctx);
+ }
+
+ @Override
+ public Node
visitDefaultPropertyValue(RelationalSqlParser.DefaultPropertyValueContext ctx) {
+ return super.visitDefaultPropertyValue(ctx);
+ }
+
+ @Override
+ public Node
visitNonDefaultPropertyValue(RelationalSqlParser.NonDefaultPropertyValueContext
ctx) {
+ return super.visitNonDefaultPropertyValue(ctx);
+ }
+
+ @Override
+ public Node visitQueryNoWith(RelationalSqlParser.QueryNoWithContext ctx) {
+ return super.visitQueryNoWith(ctx);
+ }
+
+ @Override
+ public Node visitLimitRowCount(RelationalSqlParser.LimitRowCountContext ctx)
{
+ return super.visitLimitRowCount(ctx);
+ }
+
+ @Override
+ public Node visitRowCount(RelationalSqlParser.RowCountContext ctx) {
+ return super.visitRowCount(ctx);
+ }
+
+ @Override
+ public Node
visitQueryTermDefault(RelationalSqlParser.QueryTermDefaultContext ctx) {
+ return super.visitQueryTermDefault(ctx);
+ }
+
+ @Override
+ public Node visitSetOperation(RelationalSqlParser.SetOperationContext ctx) {
+ return super.visitSetOperation(ctx);
+ }
+
+ @Override
+ public Node
visitQueryPrimaryDefault(RelationalSqlParser.QueryPrimaryDefaultContext ctx) {
+ return super.visitQueryPrimaryDefault(ctx);
+ }
+
+ @Override
+ public Node visitTable(RelationalSqlParser.TableContext ctx) {
+ return super.visitTable(ctx);
+ }
+
+ @Override
+ public Node visitInlineTable(RelationalSqlParser.InlineTableContext ctx) {
+ return super.visitInlineTable(ctx);
+ }
+
+ @Override
+ public Node visitSubquery(RelationalSqlParser.SubqueryContext ctx) {
+ return super.visitSubquery(ctx);
+ }
+
+ @Override
+ public Node visitSortItem(RelationalSqlParser.SortItemContext ctx) {
+ return super.visitSortItem(ctx);
+ }
+
+ @Override
+ public Node
visitQuerySpecification(RelationalSqlParser.QuerySpecificationContext ctx) {
+ return super.visitQuerySpecification(ctx);
+ }
+
+ @Override
+ public Node visitGroupBy(RelationalSqlParser.GroupByContext ctx) {
+ return super.visitGroupBy(ctx);
+ }
+
+ @Override
+ public Node visitTimenGrouping(RelationalSqlParser.TimenGroupingContext ctx)
{
+ return super.visitTimenGrouping(ctx);
+ }
+
+ @Override
+ public Node
visitVariationGrouping(RelationalSqlParser.VariationGroupingContext ctx) {
+ return super.visitVariationGrouping(ctx);
+ }
+
+ @Override
+ public Node
visitConditionGrouping(RelationalSqlParser.ConditionGroupingContext ctx) {
+ return super.visitConditionGrouping(ctx);
+ }
+
+ @Override
+ public Node visitSessionGrouping(RelationalSqlParser.SessionGroupingContext
ctx) {
+ return super.visitSessionGrouping(ctx);
+ }
+
+ @Override
+ public Node visitCountGrouping(RelationalSqlParser.CountGroupingContext ctx)
{
+ return super.visitCountGrouping(ctx);
+ }
+
+ @Override
+ public Node
visitSingleGroupingSet(RelationalSqlParser.SingleGroupingSetContext ctx) {
+ return super.visitSingleGroupingSet(ctx);
+ }
+
+ @Override
+ public Node visitRollup(RelationalSqlParser.RollupContext ctx) {
+ return super.visitRollup(ctx);
+ }
+
+ @Override
+ public Node visitCube(RelationalSqlParser.CubeContext ctx) {
+ return super.visitCube(ctx);
+ }
+
+ @Override
+ public Node
visitMultipleGroupingSets(RelationalSqlParser.MultipleGroupingSetsContext ctx) {
+ return super.visitMultipleGroupingSets(ctx);
+ }
+
+ @Override
+ public Node
visitLeftClosedRightOpen(RelationalSqlParser.LeftClosedRightOpenContext ctx) {
+ return super.visitLeftClosedRightOpen(ctx);
+ }
+
+ @Override
+ public Node
visitLeftOpenRightClosed(RelationalSqlParser.LeftOpenRightClosedContext ctx) {
+ return super.visitLeftOpenRightClosed(ctx);
+ }
+
+ @Override
+ public Node visitTimeValue(RelationalSqlParser.TimeValueContext ctx) {
+ return super.visitTimeValue(ctx);
+ }
+
+ @Override
+ public Node visitDateExpression(RelationalSqlParser.DateExpressionContext
ctx) {
+ return super.visitDateExpression(ctx);
+ }
+
+ @Override
+ public Node visitDatetimeLiteral(RelationalSqlParser.DatetimeLiteralContext
ctx) {
+ return super.visitDatetimeLiteral(ctx);
+ }
+
+ @Override
+ public Node visitKeepExpression(RelationalSqlParser.KeepExpressionContext
ctx) {
+ return super.visitKeepExpression(ctx);
+ }
+
+ @Override
+ public Node visitGroupingSet(RelationalSqlParser.GroupingSetContext ctx) {
+ return super.visitGroupingSet(ctx);
+ }
+
+ @Override
+ public Node visitNamedQuery(RelationalSqlParser.NamedQueryContext ctx) {
+ return super.visitNamedQuery(ctx);
+ }
+
+ @Override
+ public Node visitSetQuantifier(RelationalSqlParser.SetQuantifierContext ctx)
{
+ return super.visitSetQuantifier(ctx);
+ }
+
+ @Override
+ public Node visitSelectSingle(RelationalSqlParser.SelectSingleContext ctx) {
+ return super.visitSelectSingle(ctx);
+ }
+
+ @Override
+ public Node visitSelectAll(RelationalSqlParser.SelectAllContext ctx) {
+ return super.visitSelectAll(ctx);
+ }
+
+ @Override
+ public Node visitRelationDefault(RelationalSqlParser.RelationDefaultContext
ctx) {
+ return super.visitRelationDefault(ctx);
+ }
+
+ @Override
+ public Node visitJoinRelation(RelationalSqlParser.JoinRelationContext ctx) {
+ return super.visitJoinRelation(ctx);
+ }
+
+ @Override
+ public Node visitJoinType(RelationalSqlParser.JoinTypeContext ctx) {
+ return super.visitJoinType(ctx);
+ }
+
+ @Override
+ public Node visitJoinCriteria(RelationalSqlParser.JoinCriteriaContext ctx) {
+ return super.visitJoinCriteria(ctx);
+ }
+
+ @Override
+ public Node visitAliasedRelation(RelationalSqlParser.AliasedRelationContext
ctx) {
+ return super.visitAliasedRelation(ctx);
+ }
+
+ @Override
+ public Node visitColumnAliases(RelationalSqlParser.ColumnAliasesContext ctx)
{
+ return super.visitColumnAliases(ctx);
+ }
+
+ @Override
+ public Node visitTableName(RelationalSqlParser.TableNameContext ctx) {
+ return super.visitTableName(ctx);
+ }
+
+ @Override
+ public Node
visitSubqueryRelation(RelationalSqlParser.SubqueryRelationContext ctx) {
+ return super.visitSubqueryRelation(ctx);
+ }
+
+ @Override
+ public Node
visitParenthesizedRelation(RelationalSqlParser.ParenthesizedRelationContext
ctx) {
+ return super.visitParenthesizedRelation(ctx);
+ }
+
+ @Override
+ public Node visitExpression(RelationalSqlParser.ExpressionContext ctx) {
+ return super.visitExpression(ctx);
+ }
+
+ @Override
+ public Node visitLogicalNot(RelationalSqlParser.LogicalNotContext ctx) {
+ return super.visitLogicalNot(ctx);
+ }
+
+ @Override
+ public Node visitPredicated(RelationalSqlParser.PredicatedContext ctx) {
+ return super.visitPredicated(ctx);
+ }
+
+ @Override
+ public Node visitOr(RelationalSqlParser.OrContext ctx) {
+ return super.visitOr(ctx);
+ }
+
+ @Override
+ public Node visitAnd(RelationalSqlParser.AndContext ctx) {
+ return super.visitAnd(ctx);
+ }
+
+ @Override
+ public Node visitComparison(RelationalSqlParser.ComparisonContext ctx) {
+ return super.visitComparison(ctx);
+ }
+
+ @Override
+ public Node
visitQuantifiedComparison(RelationalSqlParser.QuantifiedComparisonContext ctx) {
+ return super.visitQuantifiedComparison(ctx);
+ }
+
+ @Override
+ public Node visitBetween(RelationalSqlParser.BetweenContext ctx) {
+ return super.visitBetween(ctx);
+ }
+
+ @Override
+ public Node visitInList(RelationalSqlParser.InListContext ctx) {
+ return super.visitInList(ctx);
+ }
+
+ @Override
+ public Node visitInSubquery(RelationalSqlParser.InSubqueryContext ctx) {
+ return super.visitInSubquery(ctx);
+ }
+
+ @Override
+ public Node visitLike(RelationalSqlParser.LikeContext ctx) {
+ return super.visitLike(ctx);
+ }
+
+ @Override
+ public Node visitNullPredicate(RelationalSqlParser.NullPredicateContext ctx)
{
+ return super.visitNullPredicate(ctx);
+ }
+
+ @Override
+ public Node visitDistinctFrom(RelationalSqlParser.DistinctFromContext ctx) {
+ return super.visitDistinctFrom(ctx);
+ }
+
+ @Override
+ public Node
visitValueExpressionDefault(RelationalSqlParser.ValueExpressionDefaultContext
ctx) {
+ return super.visitValueExpressionDefault(ctx);
+ }
+
+ @Override
+ public Node visitConcatenation(RelationalSqlParser.ConcatenationContext ctx)
{
+ return super.visitConcatenation(ctx);
+ }
+
+ @Override
+ public Node
visitArithmeticBinary(RelationalSqlParser.ArithmeticBinaryContext ctx) {
+ return super.visitArithmeticBinary(ctx);
+ }
+
+ @Override
+ public Node visitArithmeticUnary(RelationalSqlParser.ArithmeticUnaryContext
ctx) {
+ return super.visitArithmeticUnary(ctx);
+ }
+
+ @Override
+ public Node visitAtTimeZone(RelationalSqlParser.AtTimeZoneContext ctx) {
+ return super.visitAtTimeZone(ctx);
+ }
+
+ @Override
+ public Node visitDereference(RelationalSqlParser.DereferenceContext ctx) {
+ return super.visitDereference(ctx);
+ }
+
+ @Override
+ public Node visitSimpleCase(RelationalSqlParser.SimpleCaseContext ctx) {
+ return super.visitSimpleCase(ctx);
+ }
+
+ @Override
+ public Node visitColumnReference(RelationalSqlParser.ColumnReferenceContext
ctx) {
+ return super.visitColumnReference(ctx);
+ }
+
+ @Override
+ public Node
visitSpecialDateTimeFunction(RelationalSqlParser.SpecialDateTimeFunctionContext
ctx) {
+ return super.visitSpecialDateTimeFunction(ctx);
+ }
+
+ @Override
+ public Node
visitSubqueryExpression(RelationalSqlParser.SubqueryExpressionContext ctx) {
+ return super.visitSubqueryExpression(ctx);
+ }
+
+ @Override
+ public Node visitCurrentDatabase(RelationalSqlParser.CurrentDatabaseContext
ctx) {
+ return super.visitCurrentDatabase(ctx);
+ }
+
+ @Override
+ public Node visitSubstring(RelationalSqlParser.SubstringContext ctx) {
+ return super.visitSubstring(ctx);
+ }
+
+ @Override
+ public Node visitLiteral(RelationalSqlParser.LiteralContext ctx) {
+ return super.visitLiteral(ctx);
+ }
+
+ @Override
+ public Node visitCast(RelationalSqlParser.CastContext ctx) {
+ return super.visitCast(ctx);
+ }
+
+ @Override
+ public Node visitCurrentUser(RelationalSqlParser.CurrentUserContext ctx) {
+ return super.visitCurrentUser(ctx);
+ }
+
+ @Override
+ public Node
visitParenthesizedExpression(RelationalSqlParser.ParenthesizedExpressionContext
ctx) {
+ return super.visitParenthesizedExpression(ctx);
+ }
+
+ @Override
+ public Node visitTrim(RelationalSqlParser.TrimContext ctx) {
+ return super.visitTrim(ctx);
+ }
+
+ @Override
+ public Node visitFunctionCall(RelationalSqlParser.FunctionCallContext ctx) {
+ return super.visitFunctionCall(ctx);
+ }
+
+ @Override
+ public Node visitExists(RelationalSqlParser.ExistsContext ctx) {
+ return super.visitExists(ctx);
+ }
+
+ @Override
+ public Node visitSearchedCase(RelationalSqlParser.SearchedCaseContext ctx) {
+ return super.visitSearchedCase(ctx);
+ }
+
+ @Override
+ public Node visitNullLiteral(RelationalSqlParser.NullLiteralContext ctx) {
+ return super.visitNullLiteral(ctx);
+ }
+
+ @Override
+ public Node visitNumericLiteral(RelationalSqlParser.NumericLiteralContext
ctx) {
+ return super.visitNumericLiteral(ctx);
+ }
+
+ @Override
+ public Node visitBooleanLiteral(RelationalSqlParser.BooleanLiteralContext
ctx) {
+ return super.visitBooleanLiteral(ctx);
+ }
+
+ @Override
+ public Node visitStringLiteral(RelationalSqlParser.StringLiteralContext ctx)
{
+ return super.visitStringLiteral(ctx);
+ }
+
+ @Override
+ public Node visitBinaryLiteral(RelationalSqlParser.BinaryLiteralContext ctx)
{
+ return super.visitBinaryLiteral(ctx);
+ }
+
+ @Override
+ public Node visitParameter(RelationalSqlParser.ParameterContext ctx) {
+ return super.visitParameter(ctx);
+ }
+
+ @Override
+ public Node
visitTrimsSpecification(RelationalSqlParser.TrimsSpecificationContext ctx) {
+ return super.visitTrimsSpecification(ctx);
+ }
+
+ @Override
+ public Node
visitBasicStringLiteral(RelationalSqlParser.BasicStringLiteralContext ctx) {
+ return super.visitBasicStringLiteral(ctx);
+ }
+
+ @Override
+ public Node
visitUnicodeStringLiteral(RelationalSqlParser.UnicodeStringLiteralContext ctx) {
+ return super.visitUnicodeStringLiteral(ctx);
+ }
+
+ @Override
+ public Node
visitIdentifierOrString(RelationalSqlParser.IdentifierOrStringContext ctx) {
+ return super.visitIdentifierOrString(ctx);
+ }
+
+ @Override
+ public Node
visitTimeZoneInterval(RelationalSqlParser.TimeZoneIntervalContext ctx) {
+ return super.visitTimeZoneInterval(ctx);
+ }
+
+ @Override
+ public Node visitTimeZoneString(RelationalSqlParser.TimeZoneStringContext
ctx) {
+ return super.visitTimeZoneString(ctx);
+ }
+
+ @Override
+ public Node
visitComparisonOperator(RelationalSqlParser.ComparisonOperatorContext ctx) {
+ return super.visitComparisonOperator(ctx);
+ }
+
+ @Override
+ public Node
visitComparisonQuantifier(RelationalSqlParser.ComparisonQuantifierContext ctx) {
+ return super.visitComparisonQuantifier(ctx);
+ }
+
+ @Override
+ public Node visitBooleanValue(RelationalSqlParser.BooleanValueContext ctx) {
+ return super.visitBooleanValue(ctx);
+ }
+
+ @Override
+ public Node visitInterval(RelationalSqlParser.IntervalContext ctx) {
+ return super.visitInterval(ctx);
+ }
+
+ @Override
+ public Node visitIntervalField(RelationalSqlParser.IntervalFieldContext ctx)
{
+ return super.visitIntervalField(ctx);
+ }
+
+ @Override
+ public Node visitTimeDuration(RelationalSqlParser.TimeDurationContext ctx) {
+ return super.visitTimeDuration(ctx);
+ }
+
+ @Override
+ public Node visitGenericType(RelationalSqlParser.GenericTypeContext ctx) {
+ return super.visitGenericType(ctx);
+ }
+
+ @Override
+ public Node visitTypeParameter(RelationalSqlParser.TypeParameterContext ctx)
{
+ return super.visitTypeParameter(ctx);
+ }
+
+ @Override
+ public Node visitWhenClause(RelationalSqlParser.WhenClauseContext ctx) {
+ return super.visitWhenClause(ctx);
+ }
+
+ @Override
+ public Node
visitQuantifiedPrimary(RelationalSqlParser.QuantifiedPrimaryContext ctx) {
+ return super.visitQuantifiedPrimary(ctx);
+ }
+
+ @Override
+ public Node
visitPatternConcatenation(RelationalSqlParser.PatternConcatenationContext ctx) {
+ return super.visitPatternConcatenation(ctx);
+ }
+
+ @Override
+ public Node
visitPatternAlternation(RelationalSqlParser.PatternAlternationContext ctx) {
+ return super.visitPatternAlternation(ctx);
+ }
+
+ @Override
+ public Node visitPatternVariable(RelationalSqlParser.PatternVariableContext
ctx) {
+ return super.visitPatternVariable(ctx);
+ }
+
+ @Override
+ public Node visitEmptyPattern(RelationalSqlParser.EmptyPatternContext ctx) {
+ return super.visitEmptyPattern(ctx);
+ }
+
+ @Override
+ public Node
visitPatternPermutation(RelationalSqlParser.PatternPermutationContext ctx) {
+ return super.visitPatternPermutation(ctx);
+ }
+
+ @Override
+ public Node visitGroupedPattern(RelationalSqlParser.GroupedPatternContext
ctx) {
+ return super.visitGroupedPattern(ctx);
+ }
+
+ @Override
+ public Node
visitPartitionStartAnchor(RelationalSqlParser.PartitionStartAnchorContext ctx) {
+ return super.visitPartitionStartAnchor(ctx);
+ }
+
+ @Override
+ public Node
visitPartitionEndAnchor(RelationalSqlParser.PartitionEndAnchorContext ctx) {
+ return super.visitPartitionEndAnchor(ctx);
+ }
+
+ @Override
+ public Node visitExcludedPattern(RelationalSqlParser.ExcludedPatternContext
ctx) {
+ return super.visitExcludedPattern(ctx);
+ }
+
+ @Override
+ public Node
visitZeroOrMoreQuantifier(RelationalSqlParser.ZeroOrMoreQuantifierContext ctx) {
+ return super.visitZeroOrMoreQuantifier(ctx);
+ }
+
+ @Override
+ public Node
visitOneOrMoreQuantifier(RelationalSqlParser.OneOrMoreQuantifierContext ctx) {
+ return super.visitOneOrMoreQuantifier(ctx);
+ }
+
+ @Override
+ public Node
visitZeroOrOneQuantifier(RelationalSqlParser.ZeroOrOneQuantifierContext ctx) {
+ return super.visitZeroOrOneQuantifier(ctx);
+ }
+
+ @Override
+ public Node visitRangeQuantifier(RelationalSqlParser.RangeQuantifierContext
ctx) {
+ return super.visitRangeQuantifier(ctx);
+ }
+
+ @Override
+ public Node
visitUpdateAssignment(RelationalSqlParser.UpdateAssignmentContext ctx) {
+ return super.visitUpdateAssignment(ctx);
+ }
+
+ @Override
+ public Node visitReturnStatement(RelationalSqlParser.ReturnStatementContext
ctx) {
+ return super.visitReturnStatement(ctx);
+ }
+
+ @Override
+ public Node
visitAssignmentStatement(RelationalSqlParser.AssignmentStatementContext ctx) {
+ return super.visitAssignmentStatement(ctx);
+ }
+
+ @Override
+ public Node
visitSimpleCaseStatement(RelationalSqlParser.SimpleCaseStatementContext ctx) {
+ return super.visitSimpleCaseStatement(ctx);
+ }
+
+ @Override
+ public Node
visitSearchedCaseStatement(RelationalSqlParser.SearchedCaseStatementContext
ctx) {
+ return super.visitSearchedCaseStatement(ctx);
+ }
+
+ @Override
+ public Node visitIfStatement(RelationalSqlParser.IfStatementContext ctx) {
+ return super.visitIfStatement(ctx);
+ }
+
+ @Override
+ public Node
visitIterateStatement(RelationalSqlParser.IterateStatementContext ctx) {
+ return super.visitIterateStatement(ctx);
+ }
+
+ @Override
+ public Node visitLeaveStatement(RelationalSqlParser.LeaveStatementContext
ctx) {
+ return super.visitLeaveStatement(ctx);
+ }
+
+ @Override
+ public Node
visitCompoundStatement(RelationalSqlParser.CompoundStatementContext ctx) {
+ return super.visitCompoundStatement(ctx);
+ }
+
+ @Override
+ public Node visitLoopStatement(RelationalSqlParser.LoopStatementContext ctx)
{
+ return super.visitLoopStatement(ctx);
+ }
+
+ @Override
+ public Node visitWhileStatement(RelationalSqlParser.WhileStatementContext
ctx) {
+ return super.visitWhileStatement(ctx);
+ }
+
+ @Override
+ public Node visitRepeatStatement(RelationalSqlParser.RepeatStatementContext
ctx) {
+ return super.visitRepeatStatement(ctx);
+ }
+
+ @Override
+ public Node
visitCaseStatementWhenClause(RelationalSqlParser.CaseStatementWhenClauseContext
ctx) {
+ return super.visitCaseStatementWhenClause(ctx);
+ }
+
+ @Override
+ public Node visitElseIfClause(RelationalSqlParser.ElseIfClauseContext ctx) {
+ return super.visitElseIfClause(ctx);
+ }
+
+ @Override
+ public Node visitElseClause(RelationalSqlParser.ElseClauseContext ctx) {
+ return super.visitElseClause(ctx);
+ }
+
+ @Override
+ public Node
visitVariableDeclaration(RelationalSqlParser.VariableDeclarationContext ctx) {
+ return super.visitVariableDeclaration(ctx);
+ }
+
+ @Override
+ public Node
visitSqlStatementList(RelationalSqlParser.SqlStatementListContext ctx) {
+ return super.visitSqlStatementList(ctx);
+ }
+
+ @Override
+ public Node visitPrivilege(RelationalSqlParser.PrivilegeContext ctx) {
+ return super.visitPrivilege(ctx);
+ }
+
+ @Override
+ public Node visitQualifiedName(RelationalSqlParser.QualifiedNameContext ctx)
{
+ return super.visitQualifiedName(ctx);
+ }
+
+ @Override
+ public Node
visitSpecifiedPrincipal(RelationalSqlParser.SpecifiedPrincipalContext ctx) {
+ return super.visitSpecifiedPrincipal(ctx);
+ }
+
+ @Override
+ public Node
visitCurrentUserGrantor(RelationalSqlParser.CurrentUserGrantorContext ctx) {
+ return super.visitCurrentUserGrantor(ctx);
+ }
+
+ @Override
+ public Node
visitCurrentRoleGrantor(RelationalSqlParser.CurrentRoleGrantorContext ctx) {
+ return super.visitCurrentRoleGrantor(ctx);
+ }
+
+ @Override
+ public Node
visitUnspecifiedPrincipal(RelationalSqlParser.UnspecifiedPrincipalContext ctx) {
+ return super.visitUnspecifiedPrincipal(ctx);
+ }
+
+ @Override
+ public Node visitUserPrincipal(RelationalSqlParser.UserPrincipalContext ctx)
{
+ return super.visitUserPrincipal(ctx);
+ }
+
+ @Override
+ public Node visitRolePrincipal(RelationalSqlParser.RolePrincipalContext ctx)
{
+ return super.visitRolePrincipal(ctx);
+ }
+
+ @Override
+ public Node visitRoles(RelationalSqlParser.RolesContext ctx) {
+ return super.visitRoles(ctx);
+ }
+
+ @Override
+ public Node
visitUnquotedIdentifier(RelationalSqlParser.UnquotedIdentifierContext ctx) {
+ return super.visitUnquotedIdentifier(ctx);
+ }
+
+ @Override
+ public Node
visitQuotedIdentifier(RelationalSqlParser.QuotedIdentifierContext ctx) {
+ return super.visitQuotedIdentifier(ctx);
+ }
+
+ @Override
+ public Node
visitBackQuotedIdentifier(RelationalSqlParser.BackQuotedIdentifierContext ctx) {
+ return super.visitBackQuotedIdentifier(ctx);
+ }
+
+ @Override
+ public Node visitDigitIdentifier(RelationalSqlParser.DigitIdentifierContext
ctx) {
+ return super.visitDigitIdentifier(ctx);
+ }
+
+ @Override
+ public Node visitDecimalLiteral(RelationalSqlParser.DecimalLiteralContext
ctx) {
+ return super.visitDecimalLiteral(ctx);
+ }
+
+ @Override
+ public Node visitDoubleLiteral(RelationalSqlParser.DoubleLiteralContext ctx)
{
+ return super.visitDoubleLiteral(ctx);
+ }
+
+ @Override
+ public Node visitIntegerLiteral(RelationalSqlParser.IntegerLiteralContext
ctx) {
+ return super.visitIntegerLiteral(ctx);
+ }
+
+ @Override
+ public Node visitIdentifierUser(RelationalSqlParser.IdentifierUserContext
ctx) {
+ return super.visitIdentifierUser(ctx);
+ }
+
+ @Override
+ public Node visitStringUser(RelationalSqlParser.StringUserContext ctx) {
+ return super.visitStringUser(ctx);
+ }
+
+ @Override
+ public Node visitNonReserved(RelationalSqlParser.NonReservedContext ctx) {
+ return super.visitNonReserved(ctx);
+ }
+
private NodeLocation getLocation(TerminalNode terminalNode) {
requireNonNull(terminalNode, "terminalNode is null");
return getLocation(terminalNode.getSymbol());
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AllRows.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AllRows.java
new file mode 100644
index 00000000000..d2940551401
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AllRows.java
@@ -0,0 +1,67 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+
+import static java.util.Objects.requireNonNull;
+
+public final class AllRows extends Expression {
+
+ public AllRows() {
+ super(null);
+ }
+
+ public AllRows(@Nonnull NodeLocation location) {
+ super(requireNonNull(location, "location is null"));
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitAllRows(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of();
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ return (o != null) && (getClass() == o.getClass());
+ }
+
+ @Override
+ public int hashCode() {
+ return getClass().hashCode();
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ArithmeticBinaryExpression.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ArithmeticBinaryExpression.java
new file mode 100644
index 00000000000..9bcfeedbc8c
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ArithmeticBinaryExpression.java
@@ -0,0 +1,119 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static java.util.Objects.requireNonNull;
+
+public class ArithmeticBinaryExpression extends Expression {
+
+ public enum Operator {
+ ADD("+"),
+ SUBTRACT("-"),
+ MULTIPLY("*"),
+ DIVIDE("/"),
+ MODULUS("%");
+ private final String value;
+
+ Operator(String value) {
+ this.value = value;
+ }
+
+ public String getValue() {
+ return value;
+ }
+ }
+
+ private final Operator operator;
+ private final Expression left;
+ private final Expression right;
+
+ public ArithmeticBinaryExpression(Operator operator, Expression left,
Expression right) {
+ super(null);
+ this.operator = operator;
+ this.left = left;
+ this.right = right;
+ }
+
+ public ArithmeticBinaryExpression(
+ @Nonnull NodeLocation location, Operator operator, Expression left,
Expression right) {
+ super(requireNonNull(location, "location is null"));
+ this.operator = operator;
+ this.left = left;
+ this.right = right;
+ }
+
+ public Operator getOperator() {
+ return operator;
+ }
+
+ public Expression getLeft() {
+ return left;
+ }
+
+ public Expression getRight() {
+ return right;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitArithmeticBinary(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of(left, right);
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+
+ ArithmeticBinaryExpression that = (ArithmeticBinaryExpression) o;
+ return (operator == that.operator)
+ && Objects.equals(left, that.left)
+ && Objects.equals(right, that.right);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(operator, left, right);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ if (!sameClass(this, other)) {
+ return false;
+ }
+
+ return operator == ((ArithmeticBinaryExpression) other).operator;
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ArithmeticUnaryExpression.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ArithmeticUnaryExpression.java
new file mode 100644
index 00000000000..364acc94a33
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ArithmeticUnaryExpression.java
@@ -0,0 +1,114 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static java.util.Objects.requireNonNull;
+
+public class ArithmeticUnaryExpression extends Expression {
+
+ public enum Sign {
+ PLUS,
+ MINUS
+ }
+
+ private final Expression value;
+ private final Sign sign;
+
+ private ArithmeticUnaryExpression(NodeLocation location, Sign sign,
Expression value) {
+ super(location);
+ requireNonNull(value, "value is null");
+ requireNonNull(sign, "sign is null");
+
+ this.value = value;
+ this.sign = sign;
+ }
+
+ public static ArithmeticUnaryExpression positive(
+ @Nonnull NodeLocation location, Expression value) {
+ return new ArithmeticUnaryExpression(
+ requireNonNull(location, "location is null"), Sign.PLUS, value);
+ }
+
+ public static ArithmeticUnaryExpression negative(
+ @Nonnull NodeLocation location, Expression value) {
+ return new ArithmeticUnaryExpression(
+ requireNonNull(location, "location is null"), Sign.MINUS, value);
+ }
+
+ public static ArithmeticUnaryExpression positive(Expression value) {
+ return new ArithmeticUnaryExpression(null, Sign.PLUS, value);
+ }
+
+ public static ArithmeticUnaryExpression negative(Expression value) {
+ return new ArithmeticUnaryExpression(null, Sign.MINUS, value);
+ }
+
+ public Expression getValue() {
+ return value;
+ }
+
+ public Sign getSign() {
+ return sign;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitArithmeticUnary(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of(value);
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+
+ ArithmeticUnaryExpression that = (ArithmeticUnaryExpression) o;
+ return Objects.equals(value, that.value) && (sign == that.sign);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(value, sign);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ if (!sameClass(this, other)) {
+ return false;
+ }
+
+ return sign == ((ArithmeticUnaryExpression) other).sign;
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
index b8e0c07973a..607c3a1a93b 100644
---
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
@@ -34,4 +34,408 @@ public abstract class AstVisitor<R, C> {
protected R visitNode(Node node, C context) {
return null;
}
+
+ protected R visitExpression(Expression node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitCurrentTime(CurrentTime node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitArithmeticBinary(ArithmeticBinaryExpression node, C
context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitBetweenPredicate(BetweenPredicate node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitCoalesceExpression(CoalesceExpression node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitComparisonExpression(ComparisonExpression node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitLiteral(Literal node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitDoubleLiteral(DoubleLiteral node, C context) {
+ return visitLiteral(node, context);
+ }
+
+ protected R visitDecimalLiteral(DecimalLiteral node, C context) {
+ return visitLiteral(node, context);
+ }
+
+ protected R visitStatement(Statement node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitQuery(Query node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitExplain(Explain node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitExplainAnalyze(ExplainAnalyze node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitShowFunctions(ShowFunctions node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitUse(Use node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitGenericLiteral(GenericLiteral node, C context) {
+ return visitLiteral(node, context);
+ }
+
+ protected R visitWith(With node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitWithQuery(WithQuery node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitSelect(Select node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitRelation(Relation node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitQueryBody(QueryBody node, C context) {
+ return visitRelation(node, context);
+ }
+
+ protected R visitOrderBy(OrderBy node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitOffset(Offset node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitLimit(Limit node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitAllRows(AllRows node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitQuerySpecification(QuerySpecification node, C context) {
+ return visitQueryBody(node, context);
+ }
+
+ protected R visitSetOperation(SetOperation node, C context) {
+ return visitQueryBody(node, context);
+ }
+
+ protected R visitUnion(Union node, C context) {
+ return visitSetOperation(node, context);
+ }
+
+ protected R visitIntersect(Intersect node, C context) {
+ return visitSetOperation(node, context);
+ }
+
+ protected R visitExcept(Except node, C context) {
+ return visitSetOperation(node, context);
+ }
+
+ protected R visitWhenClause(WhenClause node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitInPredicate(InPredicate node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitFunctionCall(FunctionCall node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitSimpleCaseExpression(SimpleCaseExpression node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitSearchedCaseExpression(SearchedCaseExpression node, C
context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitStringLiteral(StringLiteral node, C context) {
+ return visitLiteral(node, context);
+ }
+
+ protected R visitBinaryLiteral(BinaryLiteral node, C context) {
+ return visitLiteral(node, context);
+ }
+
+ protected R visitBooleanLiteral(BooleanLiteral node, C context) {
+ return visitLiteral(node, context);
+ }
+
+ protected R visitInListExpression(InListExpression node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitIdentifier(Identifier node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitDereferenceExpression(DereferenceExpression node, C
context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitTrim(Trim node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitNullIfExpression(NullIfExpression node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitIfExpression(IfExpression node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitNullLiteral(NullLiteral node, C context) {
+ return visitLiteral(node, context);
+ }
+
+ protected R visitArithmeticUnary(ArithmeticUnaryExpression node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitNotExpression(NotExpression node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitSelectItem(SelectItem node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitSingleColumn(SingleColumn node, C context) {
+ return visitSelectItem(node, context);
+ }
+
+ protected R visitAllColumns(AllColumns node, C context) {
+ return visitSelectItem(node, context);
+ }
+
+ protected R visitLikePredicate(LikePredicate node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitIsNotNullPredicate(IsNotNullPredicate node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitIsNullPredicate(IsNullPredicate node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitLongLiteral(LongLiteral node, C context) {
+ return visitLiteral(node, context);
+ }
+
+ protected R visitParameter(Parameter node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitLogicalExpression(LogicalExpression node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitSubqueryExpression(SubqueryExpression node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitSortItem(SortItem node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitTable(Table node, C context) {
+ return visitQueryBody(node, context);
+ }
+
+ protected R visitValues(Values node, C context) {
+ return visitQueryBody(node, context);
+ }
+
+ protected R visitTableSubquery(TableSubquery node, C context) {
+ return visitQueryBody(node, context);
+ }
+
+ protected R visitAliasedRelation(AliasedRelation node, C context) {
+ return visitRelation(node, context);
+ }
+
+ protected R visitSampledRelation(SampledRelation node, C context) {
+ return visitRelation(node, context);
+ }
+
+ protected R visitJoin(Join node, C context) {
+ return visitRelation(node, context);
+ }
+
+ protected R visitExists(ExistsPredicate node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitCast(Cast node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitFieldReference(FieldReference node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitColumnDefinition(ColumnDefinition node, C context) {
+ return visitTableElement(node, context);
+ }
+
+ protected R visitCreateDB(CreateDB node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitDropDB(DropDB node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitShowDB(ShowDB node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitCreateTable(CreateTable node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitProperty(Property node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitDropTable(DropTable node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitShowTables(ShowTables node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitRenameTable(RenameTable node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitDescribeTable(DescribeTable node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitSetProperties(SetProperties node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitRenameColumn(RenameColumn node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitDropColumn(DropColumn node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitAddColumn(AddColumn node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitInsert(Insert node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitDelete(Delete node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitUpdate(Update node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitUpdateAssignment(UpdateAssignment node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitGroupBy(GroupBy node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitGroupingElement(GroupingElement node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitGroupingSets(GroupingSets node, C context) {
+ return visitGroupingElement(node, context);
+ }
+
+ protected R visitSimpleGroupBy(SimpleGroupBy node, C context) {
+ return visitGroupingElement(node, context);
+ }
+
+ protected R visitSymbolReference(SymbolReference node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R
visitQuantifiedComparisonExpression(QuantifiedComparisonExpression node, C
context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitCurrentDatabase(CurrentDatabase node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitCurrentUser(CurrentUser node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitDataType(DataType node, C context) {
+ return visitExpression(node, context);
+ }
+
+ protected R visitGenericDataType(GenericDataType node, C context) {
+ return visitDataType(node, context);
+ }
+
+ protected R visitDataTypeParameter(DataTypeParameter node, C context) {
+ return visitNode(node, context);
+ }
+
+ protected R visitNumericTypeParameter(NumericParameter node, C context) {
+ return visitDataTypeParameter(node, context);
+ }
+
+ protected R visitTypeParameter(TypeParameter node, C context) {
+ return visitDataTypeParameter(node, context);
+ }
+
+ protected R visitCreateFunction(ShowFunctions node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitCreateFunction(CreateFunction node, C context) {
+ return visitStatement(node, context);
+ }
+
+ protected R visitDropFunction(DropFunction node, C context) {
+ return visitStatement(node, context);
+ }
}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/BetweenPredicate.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/BetweenPredicate.java
new file mode 100644
index 00000000000..47905caf4b0
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/BetweenPredicate.java
@@ -0,0 +1,106 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static java.util.Objects.requireNonNull;
+
+public final class BetweenPredicate extends Expression {
+
+ private final Expression value;
+ private final Expression min;
+ private final Expression max;
+
+ public BetweenPredicate(Expression value, Expression min, Expression max) {
+ super(null);
+ requireNonNull(value, "value is null");
+ requireNonNull(min, "min is null");
+ requireNonNull(max, "max is null");
+
+ this.value = value;
+ this.min = min;
+ this.max = max;
+ }
+
+ public BetweenPredicate(
+ @Nonnull NodeLocation location, Expression value, Expression min,
Expression max) {
+ super(requireNonNull(location, "location is null"));
+ requireNonNull(value, "value is null");
+ requireNonNull(min, "min is null");
+ requireNonNull(max, "max is null");
+
+ this.value = value;
+ this.min = min;
+ this.max = max;
+ }
+
+ public Expression getValue() {
+ return value;
+ }
+
+ public Expression getMin() {
+ return min;
+ }
+
+ public Expression getMax() {
+ return max;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitBetweenPredicate(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of(value, min, max);
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+
+ BetweenPredicate that = (BetweenPredicate) o;
+ return Objects.equals(value, that.value)
+ && Objects.equals(min, that.min)
+ && Objects.equals(max, that.max);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(value, min, max);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Cast.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Cast.java
new file mode 100644
index 00000000000..c108f8e74ba
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Cast.java
@@ -0,0 +1,133 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static java.util.Objects.requireNonNull;
+
+public final class Cast extends Expression {
+ private final Expression expression;
+ private final DataType type;
+ private final boolean safe;
+ private final boolean typeOnly;
+
+ public Cast(Expression expression, DataType type) {
+ this(expression, type, false, false);
+ }
+
+ public Cast(Expression expression, DataType type, boolean safe) {
+ this(expression, type, safe, false);
+ }
+
+ public Cast(Expression expression, DataType type, boolean safe, boolean
typeOnly) {
+ super(null);
+ requireNonNull(expression, "expression is null");
+
+ this.expression = expression;
+ this.type = type;
+ this.safe = safe;
+ this.typeOnly = typeOnly;
+ }
+
+ public Cast(@Nonnull NodeLocation location, Expression expression, DataType
type) {
+ this(requireNonNull(location, "location is null"), expression, type,
false, false);
+ }
+
+ public Cast(@Nonnull NodeLocation location, Expression expression, DataType
type, boolean safe) {
+ this(requireNonNull(location, "location is null"), expression, type, safe,
false);
+ }
+
+ private Cast(
+ @Nonnull NodeLocation location,
+ Expression expression,
+ DataType type,
+ boolean safe,
+ boolean typeOnly) {
+ super(location);
+ requireNonNull(expression, "expression is null");
+
+ this.expression = expression;
+ this.type = type;
+ this.safe = safe;
+ this.typeOnly = typeOnly;
+ }
+
+ public Expression getExpression() {
+ return expression;
+ }
+
+ public DataType getType() {
+ return type;
+ }
+
+ public boolean isSafe() {
+ return safe;
+ }
+
+ public boolean isTypeOnly() {
+ return typeOnly;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitCast(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of(expression, type);
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+ Cast cast = (Cast) o;
+ return safe == cast.safe
+ && typeOnly == cast.typeOnly
+ && expression.equals(cast.expression)
+ && type.equals(cast.type);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(expression, type, safe, typeOnly);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ if (!sameClass(this, other)) {
+ return false;
+ }
+
+ Cast otherCast = (Cast) other;
+ return safe == otherCast.safe && typeOnly == otherCast.typeOnly;
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/CoalesceExpression.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/CoalesceExpression.java
new file mode 100644
index 00000000000..dcb02312c1f
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/CoalesceExpression.java
@@ -0,0 +1,92 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static com.google.common.base.Preconditions.checkArgument;
+import static java.util.Objects.requireNonNull;
+
+public final class CoalesceExpression extends Expression {
+
+ private final List<Expression> operands;
+
+ public CoalesceExpression(Expression first, Expression second, Expression...
additional) {
+ this(ImmutableList.<Expression>builder().add(first,
second).add(additional).build());
+ }
+
+ public CoalesceExpression(List<Expression> operands) {
+ super(null);
+ requireNonNull(operands, "operands is null");
+ checkArgument(operands.size() >= 2, "must have at least two operands");
+
+ this.operands = ImmutableList.copyOf(operands);
+ }
+
+ public CoalesceExpression(@Nonnull NodeLocation location, List<Expression>
operands) {
+ super(requireNonNull(location, "location is null"));
+ requireNonNull(operands, "operands is null");
+ checkArgument(operands.size() >= 2, "must have at least two operands");
+
+ this.operands = ImmutableList.copyOf(operands);
+ }
+
+ public List<Expression> getOperands() {
+ return operands;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitCoalesceExpression(this, context);
+ }
+
+ @Override
+ public List<? extends Node> getChildren() {
+ return operands;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+
+ CoalesceExpression that = (CoalesceExpression) o;
+ return Objects.equals(operands, that.operands);
+ }
+
+ @Override
+ public int hashCode() {
+ return operands.hashCode();
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ComparisonExpression.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ComparisonExpression.java
new file mode 100644
index 00000000000..f5a264ed786
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ComparisonExpression.java
@@ -0,0 +1,171 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static java.util.Objects.requireNonNull;
+
+public class ComparisonExpression extends Expression {
+
+ public enum Operator {
+ EQUAL("="),
+ NOT_EQUAL("<>"),
+ LESS_THAN("<"),
+ LESS_THAN_OR_EQUAL("<="),
+ GREATER_THAN(">"),
+ GREATER_THAN_OR_EQUAL(">="),
+ IS_DISTINCT_FROM("IS DISTINCT FROM");
+
+ private final String value;
+
+ Operator(String value) {
+ this.value = value;
+ }
+
+ public String getValue() {
+ return value;
+ }
+
+ public Operator flip() {
+ switch (this) {
+ case EQUAL:
+ return EQUAL;
+ case NOT_EQUAL:
+ return NOT_EQUAL;
+ case LESS_THAN:
+ return GREATER_THAN;
+ case LESS_THAN_OR_EQUAL:
+ return GREATER_THAN_OR_EQUAL;
+ case GREATER_THAN:
+ return LESS_THAN;
+ case GREATER_THAN_OR_EQUAL:
+ return LESS_THAN_OR_EQUAL;
+ case IS_DISTINCT_FROM:
+ return IS_DISTINCT_FROM;
+ }
+ throw new IllegalArgumentException("Unsupported comparison: " + this);
+ }
+
+ public Operator negate() {
+ switch (this) {
+ case EQUAL:
+ return NOT_EQUAL;
+ case NOT_EQUAL:
+ return EQUAL;
+ case LESS_THAN:
+ return GREATER_THAN_OR_EQUAL;
+ case LESS_THAN_OR_EQUAL:
+ return GREATER_THAN;
+ case GREATER_THAN:
+ return LESS_THAN_OR_EQUAL;
+ case GREATER_THAN_OR_EQUAL:
+ return LESS_THAN;
+ case IS_DISTINCT_FROM:
+ // Cannot negate
+ break;
+ }
+ throw new IllegalArgumentException("Unsupported comparison: " + this);
+ }
+ }
+
+ private final Operator operator;
+ private final Expression left;
+ private final Expression right;
+
+ public ComparisonExpression(Operator operator, Expression left, Expression
right) {
+ super(null);
+ requireNonNull(operator, "operator is null");
+ requireNonNull(left, "left is null");
+ requireNonNull(right, "right is null");
+
+ this.operator = operator;
+ this.left = left;
+ this.right = right;
+ }
+
+ public ComparisonExpression(
+ @Nonnull NodeLocation location, Operator operator, Expression left,
Expression right) {
+ super(requireNonNull(location, "location is null"));
+ requireNonNull(operator, "operator is null");
+ requireNonNull(left, "left is null");
+ requireNonNull(right, "right is null");
+
+ this.operator = operator;
+ this.left = left;
+ this.right = right;
+ }
+
+ public Operator getOperator() {
+ return operator;
+ }
+
+ public Expression getLeft() {
+ return left;
+ }
+
+ public Expression getRight() {
+ return right;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitComparisonExpression(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of(left, right);
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+
+ ComparisonExpression that = (ComparisonExpression) o;
+ return (operator == that.operator)
+ && Objects.equals(left, that.left)
+ && Objects.equals(right, that.right);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(operator, left, right);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ if (!sameClass(this, other)) {
+ return false;
+ }
+
+ return operator == ((ComparisonExpression) other).operator;
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/CurrentDatabase.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/CurrentDatabase.java
new file mode 100644
index 00000000000..3c05932316a
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/CurrentDatabase.java
@@ -0,0 +1,70 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+
+import static java.util.Objects.requireNonNull;
+
+public class CurrentDatabase extends Expression {
+
+ public CurrentDatabase() {
+ super(null);
+ }
+
+ public CurrentDatabase(@Nonnull NodeLocation location) {
+ super(requireNonNull(location, "location is null"));
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of();
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitCurrentDatabase(this, context);
+ }
+
+ @Override
+ public int hashCode() {
+ return getClass().hashCode();
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if ((obj == null) || (getClass() != obj.getClass())) {
+ return false;
+ }
+ return true;
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/CurrentUser.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/CurrentUser.java
new file mode 100644
index 00000000000..f995296c2f8
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/CurrentUser.java
@@ -0,0 +1,70 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+
+import static java.util.Objects.requireNonNull;
+
+public class CurrentUser extends Expression {
+
+ public CurrentUser() {
+ super(null);
+ }
+
+ public CurrentUser(@Nonnull NodeLocation location) {
+ super(requireNonNull(location, "location is null"));
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of();
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitCurrentUser(this, context);
+ }
+
+ @Override
+ public int hashCode() {
+ return getClass().hashCode();
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if ((obj == null) || (getClass() != obj.getClass())) {
+ return false;
+ }
+ return true;
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DataType.java
similarity index 76%
copy from
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
copy to
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DataType.java
index b8e0c07973a..53726ace8b3 100644
---
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DataType.java
@@ -21,17 +21,9 @@ package org.apache.iotdb.db.relational.sql.tree;
import javax.annotation.Nullable;
-public abstract class AstVisitor<R, C> {
+public abstract class DataType extends Expression {
- public R process(Node node) {
- return process(node, null);
- }
-
- public R process(Node node, @Nullable C context) {
- return node.accept(this, context);
- }
-
- protected R visitNode(Node node, C context) {
- return null;
+ DataType(@Nullable NodeLocation location) {
+ super(location);
}
}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DataTypeParameter.java
similarity index 76%
copy from
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
copy to
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DataTypeParameter.java
index b8e0c07973a..427d38c3677 100644
---
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DataTypeParameter.java
@@ -21,17 +21,14 @@ package org.apache.iotdb.db.relational.sql.tree;
import javax.annotation.Nullable;
-public abstract class AstVisitor<R, C> {
+public abstract class DataTypeParameter extends Node {
- public R process(Node node) {
- return process(node, null);
+ protected DataTypeParameter(@Nullable NodeLocation location) {
+ super(location);
}
- public R process(Node node, @Nullable C context) {
- return node.accept(this, context);
- }
-
- protected R visitNode(Node node, C context) {
- return null;
+ @Override
+ protected <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitDataTypeParameter(this, context);
}
}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DereferenceExpression.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DereferenceExpression.java
new file mode 100644
index 00000000000..76723933de5
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DereferenceExpression.java
@@ -0,0 +1,151 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nullable;
+
+import java.util.List;
+import java.util.Objects;
+import java.util.Optional;
+
+import static java.util.Objects.requireNonNull;
+
+public class DereferenceExpression extends Expression {
+
+ private final Expression base;
+ @Nullable private final Identifier field;
+
+ public DereferenceExpression(Expression base, Identifier field) {
+ super(null);
+ this.base = requireNonNull(base, "base is null");
+ this.field = requireNonNull(field, "field is null");
+ }
+
+ public DereferenceExpression(NodeLocation location, Expression base,
Identifier field) {
+ super(requireNonNull(location, "location is null"));
+ this.base = requireNonNull(base, "base is null");
+ this.field = requireNonNull(field, "field is null");
+ }
+
+ public DereferenceExpression(Identifier field) {
+ super(null);
+ this.base = null;
+ this.field = requireNonNull(field, "field is null");
+ }
+
+ public DereferenceExpression(NodeLocation location, Identifier field) {
+ super(requireNonNull(location, "location is null"));
+ this.base = null;
+ this.field = requireNonNull(field, "field is null");
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitDereferenceExpression(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ ImmutableList.Builder<Node> children = ImmutableList.builder();
+ children.add(base);
+ if (field != null) {
+ children.add(field);
+ }
+ return children.build();
+ }
+
+ public Expression getBase() {
+ return base;
+ }
+
+ public Optional<Identifier> getField() {
+ return Optional.ofNullable(field);
+ }
+
+ /**
+ * If this DereferenceExpression looks like a QualifiedName, return
QualifiedName. Otherwise
+ * return null
+ */
+ public static QualifiedName getQualifiedName(DereferenceExpression
expression) {
+ if (expression.field == null) {
+ return null;
+ }
+
+ Identifier field = expression.field;
+
+ List<Identifier> parts = null;
+ if (expression.base instanceof Identifier) {
+ parts = ImmutableList.of((Identifier) expression.base, field);
+ } else if (expression.base instanceof DereferenceExpression) {
+ QualifiedName baseQualifiedName =
getQualifiedName((DereferenceExpression) expression.base);
+ if (baseQualifiedName != null) {
+ ImmutableList.Builder<Identifier> builder = ImmutableList.builder();
+ builder.addAll(baseQualifiedName.getOriginalParts());
+ builder.add(field);
+ parts = builder.build();
+ }
+ }
+
+ return parts == null ? null : QualifiedName.of(parts);
+ }
+
+ public static Expression from(QualifiedName name) {
+ Expression result = null;
+
+ for (String part : name.getParts()) {
+ if (result == null) {
+ result = new Identifier(part);
+ } else {
+ result = new DereferenceExpression(result, new Identifier(part));
+ }
+ }
+
+ return result;
+ }
+
+ public static boolean isQualifiedAllFieldsReference(Expression expression) {
+ return expression instanceof DereferenceExpression
+ && ((DereferenceExpression) expression).field == null;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+ DereferenceExpression that = (DereferenceExpression) o;
+ return Objects.equals(base, that.base) && Objects.equals(field,
that.field);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(base, field);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DescribeTable.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DescribeTable.java
new file mode 100644
index 00000000000..f1d8c206b55
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/DescribeTable.java
@@ -0,0 +1,80 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+import static java.util.Objects.requireNonNull;
+
+public class DescribeTable extends Statement {
+ private final QualifiedName table;
+
+ public DescribeTable(QualifiedName table) {
+ super(null);
+ this.table = requireNonNull(table, "table is null");
+ }
+
+ public DescribeTable(@Nonnull NodeLocation location, QualifiedName table) {
+ super(requireNonNull(location, "location is null"));
+ this.table = requireNonNull(table, "table is null");
+ }
+
+ public QualifiedName getTable() {
+ return table;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitDescribeTable(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of();
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+ DescribeTable that = (DescribeTable) o;
+ return Objects.equals(table, that.table);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(table);
+ }
+
+ @Override
+ public String toString() {
+ return toStringHelper(this).add("table", table).toString();
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ExistsPredicate.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ExistsPredicate.java
new file mode 100644
index 00000000000..e23d13e2354
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/ExistsPredicate.java
@@ -0,0 +1,80 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static java.util.Objects.requireNonNull;
+
+public class ExistsPredicate extends Expression {
+ private final Expression subquery;
+
+ public ExistsPredicate(Expression subquery) {
+ super(null);
+ this.subquery = requireNonNull(subquery, "subquery is null");
+ }
+
+ public ExistsPredicate(@Nonnull NodeLocation location, Expression subquery) {
+ super(requireNonNull(location, "location is null"));
+ this.subquery = requireNonNull(subquery, "subquery is null");
+ }
+
+ public Expression getSubquery() {
+ return subquery;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitExists(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of(subquery);
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+
+ ExistsPredicate that = (ExistsPredicate) o;
+ return Objects.equals(subquery, that.subquery);
+ }
+
+ @Override
+ public int hashCode() {
+ return subquery.hashCode();
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Expression.java
similarity index 66%
copy from
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
copy to
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Expression.java
index b8e0c07973a..2e401eaf4cd 100644
---
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Expression.java
@@ -21,17 +21,20 @@ package org.apache.iotdb.db.relational.sql.tree;
import javax.annotation.Nullable;
-public abstract class AstVisitor<R, C> {
+public abstract class Expression extends Node {
- public R process(Node node) {
- return process(node, null);
+ protected Expression(@Nullable NodeLocation location) {
+ super(location);
}
- public R process(Node node, @Nullable C context) {
- return node.accept(this, context);
+ /** Accessible for {@link AstVisitor}, use {@link AstVisitor#process(Node,
Object)} instead. */
+ @Override
+ protected <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitExpression(this, context);
}
- protected R visitNode(Node node, C context) {
- return null;
+ @Override
+ public final String toString() {
+ return ExpressionFormatter.formatExpression(this);
}
}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/FieldReference.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/FieldReference.java
new file mode 100644
index 00000000000..ff2d7d0c2b0
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/FieldReference.java
@@ -0,0 +1,80 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import java.util.List;
+
+import static com.google.common.base.Preconditions.checkArgument;
+
+public class FieldReference extends Expression {
+
+ private final int fieldIndex;
+
+ public FieldReference(int fieldIndex) {
+ super(null);
+ checkArgument(fieldIndex >= 0, "fieldIndex must be >= 0");
+
+ this.fieldIndex = fieldIndex;
+ }
+
+ public int getFieldIndex() {
+ return fieldIndex;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitFieldReference(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of();
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+
+ FieldReference that = (FieldReference) o;
+
+ return fieldIndex == that.fieldIndex;
+ }
+
+ @Override
+ public int hashCode() {
+ return fieldIndex;
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ if (!sameClass(this, other)) {
+ return false;
+ }
+
+ return fieldIndex == ((FieldReference) other).fieldIndex;
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/FunctionCall.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/FunctionCall.java
new file mode 100644
index 00000000000..8e2b4acf355
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/FunctionCall.java
@@ -0,0 +1,113 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import java.util.List;
+import java.util.Objects;
+
+import static java.util.Objects.requireNonNull;
+
+public class FunctionCall extends Expression {
+ private final QualifiedName name;
+ private final boolean distinct;
+ private final List<Expression> arguments;
+
+ public FunctionCall(QualifiedName name, List<Expression> arguments) {
+ super(null);
+ this.name = requireNonNull(name, "name is null");
+ this.distinct = false;
+ this.arguments = requireNonNull(arguments, "arguments is null");
+ }
+
+ public FunctionCall(QualifiedName name, boolean distinct, List<Expression>
arguments) {
+ super(null);
+ this.name = requireNonNull(name, "name is null");
+ this.distinct = distinct;
+ this.arguments = requireNonNull(arguments, "arguments is null");
+ }
+
+ public FunctionCall(NodeLocation location, QualifiedName name,
List<Expression> arguments) {
+ this(location, name, false, arguments);
+ }
+
+ public FunctionCall(
+ NodeLocation location, QualifiedName name, boolean distinct,
List<Expression> arguments) {
+ super(requireNonNull(location, "location is null"));
+ this.name = requireNonNull(name, "name is null");
+ this.distinct = distinct;
+ this.arguments = requireNonNull(arguments, "arguments is null");
+ }
+
+ public QualifiedName getName() {
+ return name;
+ }
+
+ public boolean isDistinct() {
+ return distinct;
+ }
+
+ public List<Expression> getArguments() {
+ return arguments;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitFunctionCall(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ ImmutableList.Builder<Node> nodes = ImmutableList.builder();
+ nodes.addAll(arguments);
+ return nodes.build();
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if ((obj == null) || (getClass() != obj.getClass())) {
+ return false;
+ }
+ FunctionCall o = (FunctionCall) obj;
+ return Objects.equals(name, o.name)
+ && Objects.equals(distinct, o.distinct)
+ && Objects.equals(arguments, o.arguments);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(name, distinct, arguments);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ if (!sameClass(this, other)) {
+ return false;
+ }
+
+ FunctionCall otherFunction = (FunctionCall) other;
+
+ return name.equals(otherFunction.name) && distinct ==
otherFunction.distinct;
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/GenericDataType.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/GenericDataType.java
new file mode 100644
index 00000000000..99059ba7c5f
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/GenericDataType.java
@@ -0,0 +1,88 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static java.util.Objects.requireNonNull;
+
+public final class GenericDataType extends DataType {
+
+ private final Identifier name;
+ private final List<DataTypeParameter> arguments;
+
+ public GenericDataType(Identifier name, List<DataTypeParameter> arguments) {
+ super(null);
+ this.name = requireNonNull(name, "name is null");
+ this.arguments = requireNonNull(arguments, "arguments is null");
+ }
+
+ public GenericDataType(
+ @Nonnull NodeLocation location, Identifier name, List<DataTypeParameter>
arguments) {
+ super(requireNonNull(location, "location is null"));
+ this.name = requireNonNull(name, "name is null");
+ this.arguments = requireNonNull(arguments, "arguments is null");
+ }
+
+ public Identifier getName() {
+ return name;
+ }
+
+ public List<DataTypeParameter> getArguments() {
+ return arguments;
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.<Node>builder().add(name).addAll(arguments).build();
+ }
+
+ @Override
+ protected <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitGenericDataType(this, context);
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+ GenericDataType that = (GenericDataType) o;
+ return name.equals(that.name) && arguments.equals(that.arguments);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(name, arguments);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Identifier.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Identifier.java
new file mode 100644
index 00000000000..caac01cc149
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Identifier.java
@@ -0,0 +1,138 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.base.CharMatcher;
+import com.google.common.base.Strings;
+import com.google.common.collect.ImmutableList;
+
+import java.util.List;
+import java.util.Objects;
+
+import static com.google.common.base.Preconditions.checkArgument;
+import static com.google.common.base.Verify.verify;
+import static java.util.Locale.ENGLISH;
+import static java.util.Objects.requireNonNull;
+
+public class Identifier extends Expression {
+
+ private static final CharMatcher FIRST_CHAR_DISALLOWED_MATCHER =
+ CharMatcher.inRange('0', '9').precomputed();
+
+ private static final CharMatcher ALLOWED_CHARS_MATCHER =
+ CharMatcher.inRange('a', 'z')
+ .or(CharMatcher.inRange('A', 'Z'))
+ .or(CharMatcher.is('_'))
+ .or(CharMatcher.inRange('0', '9'))
+ .precomputed();
+
+ private final String value;
+ private final boolean delimited;
+
+ public Identifier(NodeLocation location, String value, boolean delimited) {
+ super(requireNonNull(location, "location is null"));
+ this.value = requireNonNull(value, "value is null");
+ this.delimited = delimited;
+
+ checkArgument(!value.isEmpty(), "value is empty");
+ checkArgument(
+ delimited || isValidIdentifier(value), "value contains illegal
characters: %s", value);
+ }
+
+ public Identifier(String value, boolean delimited) {
+ super(null);
+ this.value = requireNonNull(value, "value is null");
+ this.delimited = delimited;
+
+ checkArgument(!value.isEmpty(), "value is empty");
+ checkArgument(
+ delimited || isValidIdentifier(value), "value contains illegal
characters: %s", value);
+ }
+
+ public Identifier(String value) {
+ this(value, !isValidIdentifier(value));
+ }
+
+ public String getValue() {
+ return value;
+ }
+
+ public boolean isDelimited() {
+ return delimited;
+ }
+
+ public String getCanonicalValue() {
+ if (isDelimited()) {
+ return value;
+ }
+
+ return value.toUpperCase(ENGLISH);
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitIdentifier(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of();
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+
+ Identifier that = (Identifier) o;
+ return Objects.equals(value, that.value);
+ }
+
+ @Override
+ public int hashCode() {
+ return value.hashCode();
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ if (!sameClass(this, other)) {
+ return false;
+ }
+
+ Identifier that = (Identifier) other;
+ return Objects.equals(value, that.value) && delimited == that.delimited;
+ }
+
+ private static boolean isValidIdentifier(String value) {
+ verify(!Strings.isNullOrEmpty(value), "Identifier cannot be empty or
null");
+
+ if (FIRST_CHAR_DISALLOWED_MATCHER.matches(value.charAt(0))) {
+ return false;
+ }
+
+ // We've already checked that first char does not contain digits,
+ // so to avoid copying we are checking whole string.
+ return ALLOWED_CHARS_MATCHER.matchesAllOf(value);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/IfExpression.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/IfExpression.java
new file mode 100644
index 00000000000..097c89ee42b
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/IfExpression.java
@@ -0,0 +1,105 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nullable;
+
+import java.util.List;
+import java.util.Objects;
+import java.util.Optional;
+
+import static java.util.Objects.requireNonNull;
+
+/** IF(v1,v2[,v3]): CASE WHEN v1 THEN v2 [ELSE v3] END */
+public class IfExpression extends Expression {
+ private final Expression condition;
+ private final Expression trueValue;
+ @Nullable private final Expression falseValue;
+
+ public IfExpression(Expression condition, Expression trueValue, @Nullable
Expression falseValue) {
+ super(null);
+ this.condition = requireNonNull(condition, "condition is null");
+ this.trueValue = requireNonNull(trueValue, "trueValue is null");
+ this.falseValue = falseValue;
+ }
+
+ public IfExpression(
+ NodeLocation location,
+ Expression condition,
+ Expression trueValue,
+ @Nullable Expression falseValue) {
+ super(requireNonNull(location, "location is null"));
+ this.condition = requireNonNull(condition, "condition is null");
+ this.trueValue = requireNonNull(trueValue, "trueValue is null");
+ this.falseValue = falseValue;
+ }
+
+ public Expression getCondition() {
+ return condition;
+ }
+
+ public Expression getTrueValue() {
+ return trueValue;
+ }
+
+ public Optional<Expression> getFalseValue() {
+ return Optional.ofNullable(falseValue);
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitIfExpression(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ ImmutableList.Builder<Node> nodes = ImmutableList.builder();
+ if (falseValue != null) {
+ nodes.add(falseValue);
+ }
+ return nodes.add(condition).add(trueValue).build();
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if ((obj == null) || (getClass() != obj.getClass())) {
+ return false;
+ }
+ IfExpression o = (IfExpression) obj;
+ return Objects.equals(condition, o.condition)
+ && Objects.equals(trueValue, o.trueValue)
+ && Objects.equals(falseValue, o.falseValue);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(condition, trueValue, falseValue);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/InListExpression.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/InListExpression.java
new file mode 100644
index 00000000000..f8d263aa7e3
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/InListExpression.java
@@ -0,0 +1,83 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import java.util.List;
+import java.util.Objects;
+
+import static com.google.common.base.Preconditions.checkArgument;
+import static java.util.Objects.requireNonNull;
+
+public class InListExpression extends Expression {
+ private final List<Expression> values;
+
+ public InListExpression(List<Expression> values) {
+ super(null);
+ requireNonNull(values, "values is null");
+ checkArgument(!values.isEmpty(), "values cannot be empty");
+ this.values = ImmutableList.copyOf(values);
+ }
+
+ public InListExpression(NodeLocation location, List<Expression> values) {
+ super(requireNonNull(location, "location is null"));
+ requireNonNull(values, "values is null");
+ checkArgument(!values.isEmpty(), "values cannot be empty");
+ this.values = ImmutableList.copyOf(values);
+ }
+
+ public List<Expression> getValues() {
+ return values;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitInListExpression(this, context);
+ }
+
+ @Override
+ public List<? extends Node> getChildren() {
+ return values;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+
+ InListExpression that = (InListExpression) o;
+ return Objects.equals(values, that.values);
+ }
+
+ @Override
+ public int hashCode() {
+ return values.hashCode();
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/InPredicate.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/InPredicate.java
new file mode 100644
index 00000000000..b5233b9500d
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/InPredicate.java
@@ -0,0 +1,86 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import java.util.List;
+import java.util.Objects;
+
+import static java.util.Objects.requireNonNull;
+
+public class InPredicate extends Expression {
+
+ private final Expression value;
+ private final Expression valueList;
+
+ public InPredicate(Expression value, Expression valueList) {
+ super(null);
+ this.value = requireNonNull(value, "value is null");
+ this.valueList = requireNonNull(valueList, "valueList is null");
+ }
+
+ public InPredicate(NodeLocation location, Expression value, Expression
valueList) {
+ super(requireNonNull(location, "location is null"));
+ this.value = requireNonNull(value, "value is null");
+ this.valueList = requireNonNull(valueList, "valueList is null");
+ }
+
+ public Expression getValue() {
+ return value;
+ }
+
+ public Expression getValueList() {
+ return valueList;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitInPredicate(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of(value, valueList);
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+
+ InPredicate that = (InPredicate) o;
+ return Objects.equals(value, that.value) && Objects.equals(valueList,
that.valueList);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(value, valueList);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Literal.java
similarity index 69%
copy from
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
copy to
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Literal.java
index b8e0c07973a..b61b0bbb9cd 100644
---
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Literal.java
@@ -19,19 +19,24 @@
package org.apache.iotdb.db.relational.sql.tree;
+import com.google.common.collect.ImmutableList;
+
import javax.annotation.Nullable;
-public abstract class AstVisitor<R, C> {
+import java.util.List;
- public R process(Node node) {
- return process(node, null);
+public abstract class Literal extends Expression {
+ protected Literal(@Nullable NodeLocation location) {
+ super(location);
}
- public R process(Node node, @Nullable C context) {
- return node.accept(this, context);
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitLiteral(this, context);
}
- protected R visitNode(Node node, C context) {
- return null;
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of();
}
}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Node.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Node.java
index 0c3ec9b8e32..96797b308f3 100644
---
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Node.java
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Node.java
@@ -41,7 +41,7 @@ public abstract class Node {
return Optional.ofNullable(location);
}
- public abstract List<Node> getChildren();
+ public abstract List<? extends Node> getChildren();
// Force subclasses to have a proper equals and hashcode implementation
@Override
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/NumericParameter.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/NumericParameter.java
new file mode 100644
index 00000000000..7d2c5e1e657
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/NumericParameter.java
@@ -0,0 +1,88 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static java.util.Objects.requireNonNull;
+
+public class NumericParameter extends DataTypeParameter {
+ private final String value;
+
+ public NumericParameter(String value) {
+ super(null);
+ this.value = requireNonNull(value, "value is null");
+ }
+
+ public NumericParameter(@Nonnull NodeLocation location, String value) {
+ super(requireNonNull(location, "location is null"));
+ this.value = requireNonNull(value, "value is null");
+ }
+
+ public String getValue() {
+ return value;
+ }
+
+ @Override
+ public String toString() {
+ return value;
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of();
+ }
+
+ @Override
+ protected <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitNumericTypeParameter(this, context);
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+ NumericParameter that = (NumericParameter) o;
+ return value.equals(that.value);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(value);
+ }
+
+ @Override
+ public boolean shallowEquals(Node other) {
+ if (!sameClass(this, other)) {
+ return false;
+ }
+
+ return Objects.equals(value, ((NumericParameter) other).value);
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Property.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Property.java
new file mode 100644
index 00000000000..653fab420dd
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Property.java
@@ -0,0 +1,120 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+import javax.annotation.Nullable;
+
+import java.util.List;
+import java.util.Objects;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+import static com.google.common.base.Preconditions.checkState;
+import static java.util.Objects.requireNonNull;
+
+public class Property extends Node {
+ private final Identifier name;
+
+ @Nullable private final Expression value; // null iff the value is set to
DEFAULT
+
+ /** Constructs an instance representing a property whose value is set to
DEFAULT */
+ public Property(@Nonnull Identifier name) {
+ super(null);
+ this.name = requireNonNull(name, "name is null");
+ this.value = null;
+ }
+
+ /** Constructs an instance representing a property whose value is set to
DEFAULT */
+ public Property(@Nonnull NodeLocation location, @Nonnull Identifier name) {
+ super(requireNonNull(location, "location is null"));
+ this.name = requireNonNull(name, "name is null");
+ this.value = null;
+ }
+
+ public Property(@Nonnull Identifier name, @Nonnull Expression value) {
+ super(null);
+ this.name = requireNonNull(name, "name is null");
+ this.value = requireNonNull(value, "value is null");
+ }
+
+ public Property(
+ @Nonnull NodeLocation location, @Nonnull Identifier name, @Nullable
Expression value) {
+ super(requireNonNull(location, "location is null"));
+ this.name = requireNonNull(name, "name is null");
+ this.value = requireNonNull(value, "value is null");
+ }
+
+ public Identifier getName() {
+ return name;
+ }
+
+ public boolean isSetToDefault() {
+ return value == null;
+ }
+
+ /**
+ * Returns the non-default value of the property. This method should be
called only if the
+ * property is not set to DEFAULT.
+ */
+ public Expression getNonDefaultValue() {
+ checkState(
+ !isSetToDefault(),
+ "Cannot get non-default value of property %s since its value is set to
DEFAULT",
+ name);
+ return value;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitProperty(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return isSetToDefault() ? ImmutableList.of(name) : ImmutableList.of(name,
getNonDefaultValue());
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if (obj == null || getClass() != obj.getClass()) {
+ return false;
+ }
+ Property other = (Property) obj;
+ return Objects.equals(name, other.name) && Objects.equals(value,
other.value);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(name, value);
+ }
+
+ @Override
+ public String toString() {
+ return toStringHelper(this)
+ .add("name", name)
+ .add("value", isSetToDefault() ? "DEFAULT" : getNonDefaultValue())
+ .toString();
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/QualifiedName.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/QualifiedName.java
new file mode 100644
index 00000000000..4b62f96b85f
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/QualifiedName.java
@@ -0,0 +1,139 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+import com.google.common.collect.Lists;
+
+import javax.annotation.Nullable;
+
+import java.util.List;
+import java.util.Optional;
+
+import static com.google.common.base.Preconditions.checkArgument;
+import static com.google.common.collect.ImmutableList.toImmutableList;
+import static com.google.common.collect.Iterables.isEmpty;
+import static java.util.Locale.ENGLISH;
+import static java.util.Objects.requireNonNull;
+
+public class QualifiedName {
+
+ private final List<Identifier> originalParts;
+ private final List<String> parts;
+
+ // Following fields are not part of the equals/hashCode methods as
+ // they are exist solely to speed-up certain method calls.
+ private final String name;
+
+ @Nullable private final QualifiedName prefix;
+ private final String suffix;
+
+ public static QualifiedName of(String first, String... rest) {
+ requireNonNull(first, "first is null");
+ return of(Lists.asList(first,
rest).stream().map(Identifier::new).collect(toImmutableList()));
+ }
+
+ public static QualifiedName of(String name) {
+ requireNonNull(name, "name is null");
+ return of(ImmutableList.of(new Identifier(name)));
+ }
+
+ public static QualifiedName of(Iterable<Identifier> originalParts) {
+ requireNonNull(originalParts, "originalParts is null");
+ checkArgument(!isEmpty(originalParts), "originalParts is empty");
+
+ return new QualifiedName(ImmutableList.copyOf(originalParts));
+ }
+
+ private QualifiedName(List<Identifier> originalParts) {
+ this.originalParts = originalParts;
+ // Iteration instead of stream for performance reasons
+ ImmutableList.Builder<String> partsBuilder =
+ ImmutableList.builderWithExpectedSize(originalParts.size());
+ for (Identifier identifier : originalParts) {
+ partsBuilder.add(mapIdentifier(identifier));
+ }
+ this.parts = partsBuilder.build();
+ this.name = String.join(".", parts);
+
+ if (originalParts.size() == 1) {
+ this.prefix = null;
+ this.suffix = mapIdentifier(originalParts.get(0));
+ } else {
+ List<Identifier> subList = originalParts.subList(0, originalParts.size()
- 1);
+ this.prefix = new QualifiedName(subList);
+ this.suffix = mapIdentifier(originalParts.get(originalParts.size() - 1));
+ }
+ }
+
+ private static String mapIdentifier(Identifier identifier) {
+ return identifier.getValue().toLowerCase(ENGLISH);
+ }
+
+ public List<String> getParts() {
+ return parts;
+ }
+
+ public List<Identifier> getOriginalParts() {
+ return originalParts;
+ }
+
+ /**
+ * For an identifier of the form "a.b.c.d", returns "a.b.c" For an
identifier of the form "a",
+ * returns absent
+ */
+ public Optional<QualifiedName> getPrefix() {
+ return Optional.ofNullable(this.prefix);
+ }
+
+ public boolean hasSuffix(QualifiedName suffix) {
+ if (parts.size() < suffix.getParts().size()) {
+ return false;
+ }
+
+ int start = parts.size() - suffix.getParts().size();
+ return parts.subList(start, parts.size()).equals(suffix.getParts());
+ }
+
+ public String getSuffix() {
+ return this.suffix;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+ return parts.equals(((QualifiedName) o).parts);
+ }
+
+ @Override
+ public int hashCode() {
+ return parts.hashCode();
+ }
+
+ @Override
+ public String toString() {
+ return name;
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/SetProperties.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/SetProperties.java
new file mode 100644
index 00000000000..f6e9227cd4a
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/SetProperties.java
@@ -0,0 +1,107 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+import static java.util.Objects.requireNonNull;
+
+public class SetProperties extends Statement {
+
+ public enum Type {
+ TABLE,
+ MATERIALIZED_VIEW
+ }
+
+ private final Type type;
+ private final QualifiedName name;
+ private final List<Property> properties;
+
+ public SetProperties(Type type, QualifiedName name, List<Property>
properties) {
+ super(null);
+ this.type = requireNonNull(type, "type is null");
+ this.name = requireNonNull(name, "name is null");
+ this.properties = ImmutableList.copyOf(requireNonNull(properties,
"properties is null"));
+ }
+
+ public SetProperties(
+ @Nonnull NodeLocation location, Type type, QualifiedName name,
List<Property> properties) {
+ super(requireNonNull(location, "location is null"));
+ this.type = requireNonNull(type, "type is null");
+ this.name = requireNonNull(name, "name is null");
+ this.properties = ImmutableList.copyOf(requireNonNull(properties,
"properties is null"));
+ }
+
+ public Type getType() {
+ return type;
+ }
+
+ public QualifiedName getName() {
+ return name;
+ }
+
+ public List<Property> getProperties() {
+ return properties;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitSetProperties(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of();
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(type, name, properties);
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if ((obj == null) || (getClass() != obj.getClass())) {
+ return false;
+ }
+ SetProperties o = (SetProperties) obj;
+ return type == o.type
+ && Objects.equals(name, o.name)
+ && Objects.equals(properties, o.properties);
+ }
+
+ @Override
+ public String toString() {
+ return toStringHelper(this)
+ .add("type", type)
+ .add("name", name)
+ .add("properties", properties)
+ .toString();
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Statement.java
similarity index 77%
copy from
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
copy to
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Statement.java
index b8e0c07973a..39fa39ba136 100644
---
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/AstVisitor.java
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Statement.java
@@ -21,17 +21,14 @@ package org.apache.iotdb.db.relational.sql.tree;
import javax.annotation.Nullable;
-public abstract class AstVisitor<R, C> {
+public abstract class Statement extends Node {
- public R process(Node node) {
- return process(node, null);
+ protected Statement(@Nullable NodeLocation location) {
+ super(location);
}
- public R process(Node node, @Nullable C context) {
- return node.accept(this, context);
- }
-
- protected R visitNode(Node node, C context) {
- return null;
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitStatement(this, context);
}
}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Node.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/TypeParameter.java
similarity index 51%
copy from
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Node.java
copy to
iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/TypeParameter.java
index 0c3ec9b8e32..4970cc479a8 100644
---
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Node.java
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/TypeParameter.java
@@ -19,53 +19,60 @@
package org.apache.iotdb.db.relational.sql.tree;
-import javax.annotation.Nullable;
+import com.google.common.collect.ImmutableList;
import java.util.List;
-import java.util.Optional;
+import java.util.Objects;
-public abstract class Node {
+import static java.util.Objects.requireNonNull;
- @Nullable private final NodeLocation location;
+public class TypeParameter extends DataTypeParameter {
- protected Node(@Nullable NodeLocation location) {
- this.location = location;
- }
+ private final DataType type;
- /** Accessible for {@link AstVisitor}, use {@link AstVisitor#process(Node,
Object)} instead. */
- protected <R, C> R accept(AstVisitor<R, C> visitor, C context) {
- return visitor.visitNode(this, context);
+ public TypeParameter(DataType type) {
+ super(null);
+ this.type = requireNonNull(type, "type is null");
}
- public Optional<NodeLocation> getLocation() {
- return Optional.ofNullable(location);
+ public DataType getValue() {
+ return type;
}
- public abstract List<Node> getChildren();
-
- // Force subclasses to have a proper equals and hashcode implementation
@Override
- public abstract int hashCode();
+ public String toString() {
+ return type.toString();
+ }
@Override
- public abstract boolean equals(Object obj);
+ public List<Node> getChildren() {
+ return ImmutableList.of(type);
+ }
@Override
- public abstract String toString();
-
- /**
- * Compare with another node by considering internal state excluding any
Node returned by
- * getChildren()
- */
- public boolean shallowEquals(Node other) {
- throw new UnsupportedOperationException("not yet implemented: " +
getClass().getName());
+ protected <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitTypeParameter(this, context);
}
- static boolean sameClass(Node left, Node right) {
- if (left == right) {
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
return true;
}
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+ TypeParameter that = (TypeParameter) o;
+ return type.equals(that.type);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(type);
+ }
- return left.getClass() == right.getClass();
+ @Override
+ public boolean shallowEquals(Node other) {
+ return sameClass(this, other);
}
}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Use.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Use.java
new file mode 100644
index 00000000000..d94ce5c9f70
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/tree/Use.java
@@ -0,0 +1,81 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.tree;
+
+import com.google.common.collect.ImmutableList;
+
+import javax.annotation.Nonnull;
+
+import java.util.List;
+import java.util.Objects;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+import static java.util.Objects.requireNonNull;
+
+public final class Use extends Statement {
+
+ private final Identifier db;
+
+ public Use(@Nonnull Identifier db) {
+ super(null);
+ this.db = requireNonNull(db, "db is null");
+ }
+
+ public Use(@Nonnull NodeLocation location, @Nonnull Identifier db) {
+ super(requireNonNull(location, "location is null"));
+ this.db = requireNonNull(db, "db is null");
+ }
+
+ public Identifier getDatabase() {
+ return db;
+ }
+
+ @Override
+ public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
+ return visitor.visitUse(this, context);
+ }
+
+ @Override
+ public List<Node> getChildren() {
+ return ImmutableList.of();
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (o == null || getClass() != o.getClass()) {
+ return false;
+ }
+ Use use = (Use) o;
+ return Objects.equals(db, use.db);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(db);
+ }
+
+ @Override
+ public String toString() {
+ return toStringHelper(this).toString();
+ }
+}
diff --git
a/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/util/ExpressionFormatter.java
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/util/ExpressionFormatter.java
new file mode 100644
index 00000000000..de9ac00e13c
--- /dev/null
+++
b/iotdb-core/relational-parser/src/main/java/org/apache/iotdb/db/relational/sql/util/ExpressionFormatter.java
@@ -0,0 +1,50 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.db.relational.sql.util;
+
+import org.apache.iotdb.db.relational.sql.tree.AstVisitor;
+import org.apache.iotdb.db.relational.sql.tree.Expression;
+
+import java.util.Optional;
+import java.util.function.Function;
+
+import static java.util.Objects.requireNonNull;
+
+public final class ExpressionFormatter {
+
+ private ExpressionFormatter() {}
+
+ public static String formatExpression(Expression expression) {
+ return new Formatter(Optional.empty(),
Optional.empty()).process(expression, null);
+ }
+
+ public static class Formatter extends AstVisitor<String, Void> {
+ private final Optional<Function<Literal, String>> literalFormatter;
+ private final Optional<Function<SymbolReference, String>>
symbolReferenceFormatter;
+
+ public Formatter(
+ Optional<Function<Literal, String>> literalFormatter,
+ Optional<Function<SymbolReference, String>> symbolReferenceFormatter) {
+ this.literalFormatter = requireNonNull(literalFormatter,
"literalFormatter is null");
+ this.symbolReferenceFormatter =
+ requireNonNull(symbolReferenceFormatter, "symbolReferenceFormatter
is null");
+ }
+ }
+}