package com.taobao.tddl.optimizer.costbased.esitimater; import com.taobao.tddl.optimizer.core.ast.ASTNode; import com.taobao.tddl.optimizer.core.ast.QueryTreeNode; import com.taobao.tddl.optimizer.core.ast.query.MergeNode; import com.taobao.tddl.optimizer.exceptions.StatisticsUnavailableException; /** * @author Dreamond */ public class MergeNodeCostEstimater implements QueryTreeCostEstimater { @Override public Cost estimate(QueryTreeNode query) throws StatisticsUnavailableException { MergeNode merge = (MergeNode) query; Cost cost = new Cost(); long rowCount = 0; long io = 0; long networkCost = 0; long scanRowCount = 0; if (!(merge.getChildren().get(0) instanceof QueryTreeNode)) { return cost; } for (ASTNode sub : merge.getChildren()) { Cost subCost = CostEsitimaterFactory.estimate((QueryTreeNode) sub); rowCount += subCost.getRowCount(); scanRowCount += subCost.getScanCount(); // 如果两个不在一个节点上,就会产生网络开销,需要把sub的数据传送到merge节点上 if (merge.getDataNode() != null) { if (!merge.getDataNode().equals(sub.getDataNode())) { networkCost += subCost.getRowCount(); } } } if (query.getLimitFrom() != null && (query.getLimitFrom() instanceof Long || query.getLimitFrom() instanceof Long) && (Long) query.getLimitFrom() != 0 && query.getLimitTo() != null && (query.getLimitTo() instanceof Long || query.getLimitTo() instanceof Long) && (Long) query.getLimitTo() != 0) { rowCount = ((Long) query.getLimitTo() - (Long) query.getLimitFrom()); } cost.setRowCount(rowCount); cost.setDiskIO(io); cost.setNetworkCost(networkCost); cost.setIsOnFly(true); cost.setScanCount(scanRowCount); return cost; } }