Skip to content

Commit

Permalink
for #2567, move SelectItemsEngine.appendAverageDerivedColumns to Sele…
Browse files Browse the repository at this point in the history
…ctItemEngine
  • Loading branch information
terrymanu committed Jul 13, 2019
1 parent 8581a4c commit c822f4c
Show file tree
Hide file tree
Showing 2 changed files with 54 additions and 58 deletions.
Expand Up @@ -18,6 +18,7 @@
package org.apache.shardingsphere.core.optimize.statement.sharding.dml.select.item.engine;

import com.google.common.base.Optional;
import org.apache.shardingsphere.core.constant.AggregationType;
import org.apache.shardingsphere.core.optimize.statement.sharding.dml.select.item.AggregationDistinctSelectItem;
import org.apache.shardingsphere.core.optimize.statement.sharding.dml.select.item.AggregationSelectItem;
import org.apache.shardingsphere.core.optimize.statement.sharding.dml.select.item.CommonSelectItem;
Expand All @@ -34,13 +35,15 @@
import org.apache.shardingsphere.core.parse.sql.statement.SQLStatement;

/**
* Select items engine.
* Select item engine.
*
* @author zhangliang
*/
public final class SelectItemEngine {

private int derivedColumnCount;
private int aggregationAverageDerivedColumnCount;

private int aggregationDistinctDerivedColumnCount;

/**
* Create select item.
Expand All @@ -51,40 +54,77 @@ public final class SelectItemEngine {
*/
public Optional<SelectItem> createSelectItem(final SelectItemSegment selectItemSegment, final SQLStatement sqlStatement) {
if (selectItemSegment instanceof ShorthandSelectItemSegment) {
return Optional.<SelectItem>of(createShorthandSelectItemSegment((ShorthandSelectItemSegment) selectItemSegment));
return Optional.<SelectItem>of(createSelectItem((ShorthandSelectItemSegment) selectItemSegment));
}
if (selectItemSegment instanceof ColumnSelectItemSegment) {
return Optional.<SelectItem>of(createColumnSelectItemSegment((ColumnSelectItemSegment) selectItemSegment));
return Optional.<SelectItem>of(createSelectItem((ColumnSelectItemSegment) selectItemSegment));
}
if (selectItemSegment instanceof ExpressionSelectItemSegment) {
return Optional.<SelectItem>of(createExpressionSelectItemSegment((ExpressionSelectItemSegment) selectItemSegment));
return Optional.<SelectItem>of(createSelectItem((ExpressionSelectItemSegment) selectItemSegment));
}
if (selectItemSegment instanceof AggregationDistinctSelectItemSegment) {
return Optional.<SelectItem>of(createSelectItem((AggregationDistinctSelectItemSegment) selectItemSegment, sqlStatement));
}
if (selectItemSegment instanceof AggregationSelectItemSegment) {
return Optional.<SelectItem>of(createAggregationSelectItemSegment((AggregationSelectItemSegment) selectItemSegment, sqlStatement));
return Optional.<SelectItem>of(createSelectItem((AggregationSelectItemSegment) selectItemSegment, sqlStatement));
}
// TODO subquery
return Optional.absent();
}

private ShorthandSelectItem createShorthandSelectItemSegment(final ShorthandSelectItemSegment selectItemSegment) {
private ShorthandSelectItem createSelectItem(final ShorthandSelectItemSegment selectItemSegment) {
Optional<TableSegment> owner = selectItemSegment.getOwner();
return new ShorthandSelectItem(owner.isPresent() ? owner.get().getName() : null);
}

private CommonSelectItem createColumnSelectItemSegment(final ColumnSelectItemSegment selectItemSegment) {
private CommonSelectItem createSelectItem(final ColumnSelectItemSegment selectItemSegment) {
return new CommonSelectItem(selectItemSegment.getQualifiedName(), selectItemSegment.getAlias().orNull());
}

private CommonSelectItem createExpressionSelectItemSegment(final ExpressionSelectItemSegment selectItemSegment) {
private CommonSelectItem createSelectItem(final ExpressionSelectItemSegment selectItemSegment) {
return new CommonSelectItem(selectItemSegment.getText(), selectItemSegment.getAlias().orNull());
}

private AggregationSelectItem createAggregationSelectItemSegment(final AggregationSelectItemSegment selectItemSegment, final SQLStatement sqlStatement) {
private AggregationDistinctSelectItem createSelectItem(final AggregationDistinctSelectItemSegment selectItemSegment, final SQLStatement sqlStatement) {
String innerExpression = sqlStatement.getLogicSQL().substring(selectItemSegment.getInnerExpressionStartIndex(), selectItemSegment.getStopIndex() + 1);
if (selectItemSegment instanceof AggregationDistinctSelectItemSegment) {
String alias = selectItemSegment.getAlias().or(DerivedColumn.AGGREGATION_DISTINCT_DERIVED.getDerivedColumnAlias(derivedColumnCount++));
return new AggregationDistinctSelectItem(selectItemSegment.getType(), innerExpression, alias, ((AggregationDistinctSelectItemSegment) selectItemSegment).getDistinctExpression());
String alias = selectItemSegment.getAlias().or(DerivedColumn.AGGREGATION_DISTINCT_DERIVED.getDerivedColumnAlias(aggregationDistinctDerivedColumnCount++));
AggregationDistinctSelectItem result = new AggregationDistinctSelectItem(selectItemSegment.getType(), innerExpression, alias, selectItemSegment.getDistinctExpression());
if (AggregationType.AVG == result.getType()) {
appendAverageDistinctDerivedItem(result);
}
return result;
}

private AggregationSelectItem createSelectItem(final AggregationSelectItemSegment selectItemSegment, final SQLStatement sqlStatement) {
String innerExpression = sqlStatement.getLogicSQL().substring(selectItemSegment.getInnerExpressionStartIndex(), selectItemSegment.getStopIndex() + 1);
AggregationSelectItem result = new AggregationSelectItem(selectItemSegment.getType(), innerExpression, selectItemSegment.getAlias().orNull());
if (AggregationType.AVG == result.getType()) {
appendAverageDerivedItem(result);
// TODO replace avg to constant, avoid calculate useless avg
}
return new AggregationSelectItem(selectItemSegment.getType(), innerExpression, selectItemSegment.getAlias().orNull());
return result;
}

private void appendAverageDistinctDerivedItem(final AggregationDistinctSelectItem averageDistinctSelectItem) {
String innerExpression = averageDistinctSelectItem.getInnerExpression();
String distinctInnerExpression = averageDistinctSelectItem.getDistinctInnerExpression();
String countAlias = DerivedColumn.AVG_COUNT_ALIAS.getDerivedColumnAlias(aggregationAverageDerivedColumnCount);
AggregationDistinctSelectItem countDistinctSelectItem = new AggregationDistinctSelectItem(AggregationType.COUNT, innerExpression, countAlias, distinctInnerExpression);
String sumAlias = DerivedColumn.AVG_SUM_ALIAS.getDerivedColumnAlias(aggregationAverageDerivedColumnCount);
AggregationDistinctSelectItem sumDistinctSelectItem = new AggregationDistinctSelectItem(AggregationType.SUM, innerExpression, sumAlias, distinctInnerExpression);
averageDistinctSelectItem.getDerivedAggregationItems().add(countDistinctSelectItem);
averageDistinctSelectItem.getDerivedAggregationItems().add(sumDistinctSelectItem);
aggregationAverageDerivedColumnCount++;
}

private void appendAverageDerivedItem(final AggregationSelectItem averageSelectItem) {
String innerExpression = averageSelectItem.getInnerExpression();
String countAlias = DerivedColumn.AVG_COUNT_ALIAS.getDerivedColumnAlias(aggregationAverageDerivedColumnCount);
AggregationSelectItem countSelectItem = new AggregationSelectItem(AggregationType.COUNT, innerExpression, countAlias);
String sumAlias = DerivedColumn.AVG_SUM_ALIAS.getDerivedColumnAlias(aggregationAverageDerivedColumnCount);
AggregationSelectItem sumSelectItem = new AggregationSelectItem(AggregationType.SUM, innerExpression, sumAlias);
averageSelectItem.getDerivedAggregationItems().add(countSelectItem);
averageSelectItem.getDerivedAggregationItems().add(sumSelectItem);
aggregationAverageDerivedColumnCount++;
}
}
Expand Up @@ -20,11 +20,8 @@
import com.google.common.base.Optional;
import com.google.common.base.Preconditions;
import lombok.RequiredArgsConstructor;
import org.apache.shardingsphere.core.constant.AggregationType;
import org.apache.shardingsphere.core.metadata.table.ShardingTableMetaData;
import org.apache.shardingsphere.core.optimize.statement.sharding.dml.select.groupby.GroupBy;
import org.apache.shardingsphere.core.optimize.statement.sharding.dml.select.item.AggregationDistinctSelectItem;
import org.apache.shardingsphere.core.optimize.statement.sharding.dml.select.item.AggregationSelectItem;
import org.apache.shardingsphere.core.optimize.statement.sharding.dml.select.item.DerivedCommonSelectItem;
import org.apache.shardingsphere.core.optimize.statement.sharding.dml.select.item.SelectItem;
import org.apache.shardingsphere.core.optimize.statement.sharding.dml.select.item.SelectItems;
Expand Down Expand Up @@ -68,7 +65,6 @@ public final class SelectItemsEngine {
public SelectItems createSelectItems(final SelectStatement selectStatement, final GroupBy groupBy, final OrderBy orderBy) {
SelectItemsSegment selectItemsSegment = getSelectItemsSegment(selectStatement);
Collection<SelectItem> items = getSelectItemList(selectItemsSegment, selectStatement);
appendAverageDerivedColumns(items);
items.addAll(getDerivedGroupByColumns(selectStatement, items, groupBy.getItems()));
items.addAll(getDerivedOrderByColumns(selectStatement, items, orderBy.getItems()));
SelectItems result = new SelectItems(items, selectItemsSegment.isDistinctRow(), selectItemsSegment.getStopIndex());
Expand All @@ -93,46 +89,6 @@ private Collection<SelectItem> getSelectItemList(final SelectItemsSegment select
return result;
}

private void appendAverageDerivedColumns(final Collection<SelectItem> items) {
int derivedColumnOffset = 0;
for (SelectItem each : items) {
if (each instanceof AggregationSelectItem && AggregationType.AVG == ((AggregationSelectItem) each).getType()) {
appendAverageDerivedColumns(derivedColumnOffset++, each);
// TODO replace avg to constant, avoid calculate useless avg
}
}
}

private void appendAverageDerivedColumns(final int derivedColumnOffset, final SelectItem selectItem) {
if (selectItem instanceof AggregationDistinctSelectItem) {
appendDerivedAggregationDistinctSelectItems((AggregationDistinctSelectItem) selectItem, derivedColumnOffset);
} else {
appendDerivedAggregationSelectItems((AggregationSelectItem) selectItem, derivedColumnOffset);
}
}

private void appendDerivedAggregationDistinctSelectItems(final AggregationDistinctSelectItem averageDistinctSelectItem, final int derivedColumnOffset) {
String countAlias = DerivedColumn.AVG_COUNT_ALIAS.getDerivedColumnAlias(derivedColumnOffset);
AggregationDistinctSelectItem countDistinctSelectItem = new AggregationDistinctSelectItem(
AggregationType.COUNT, averageDistinctSelectItem.getInnerExpression(), countAlias, averageDistinctSelectItem.getDistinctInnerExpression());
String sumAlias = DerivedColumn.AVG_SUM_ALIAS.getDerivedColumnAlias(derivedColumnOffset);
AggregationDistinctSelectItem sumDistinctSelectItem = new AggregationDistinctSelectItem(
AggregationType.SUM, averageDistinctSelectItem.getInnerExpression(), sumAlias, averageDistinctSelectItem.getDistinctInnerExpression());
averageDistinctSelectItem.getDerivedAggregationItems().clear();
averageDistinctSelectItem.getDerivedAggregationItems().add(countDistinctSelectItem);
averageDistinctSelectItem.getDerivedAggregationItems().add(sumDistinctSelectItem);
}

private void appendDerivedAggregationSelectItems(final AggregationSelectItem averageSelectItem, final int derivedColumnOffset) {
String countAlias = DerivedColumn.AVG_COUNT_ALIAS.getDerivedColumnAlias(derivedColumnOffset);
AggregationSelectItem countSelectItem = new AggregationSelectItem(AggregationType.COUNT, averageSelectItem.getInnerExpression(), countAlias);
String sumAlias = DerivedColumn.AVG_SUM_ALIAS.getDerivedColumnAlias(derivedColumnOffset);
AggregationSelectItem sumSelectItem = new AggregationSelectItem(AggregationType.SUM, averageSelectItem.getInnerExpression(), sumAlias);
averageSelectItem.getDerivedAggregationItems().clear();
averageSelectItem.getDerivedAggregationItems().add(countSelectItem);
averageSelectItem.getDerivedAggregationItems().add(sumSelectItem);
}

private Collection<SelectItem> getDerivedGroupByColumns(final SelectStatement selectStatement, final Collection<SelectItem> selectItems, final Collection<OrderByItem> groupByItems) {
return getDerivedOrderColumns(selectStatement, selectItems, groupByItems, DerivedColumn.GROUP_BY_ALIAS);
}
Expand Down

0 comments on commit c822f4c

Please sign in to comment.