You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@calcite.apache.org by jh...@apache.org on 2018/12/02 00:54:57 UTC
[05/15] calcite git commit: [CALCITE-2632] Ensure that RexNode and
its sub-classes implement hashCode and equals methods (Zoltan Haindrich)
[CALCITE-2632] Ensure that RexNode and its sub-classes implement hashCode and equals methods (Zoltan Haindrich)
Previously there was no default hashCode/equals implementations. To
ensure that they are working properly is crucial while working with
basic collections like sets/maps.
Fix ups (Julian Hyde):
* Use Objects.equals(x, y) in preference to x.equals(y) only when x or y
may be null; and use x == y when objects are primitive.
* When implementing Object.equals, use the pattern
return this == obj
|| obj instanceof Type
&& a.equals(((Type) obj).a) ...
whenever possible.
* In the many cases where RexNode.toString() is used as a key in
collections, use the raw RexNode instead.
Close apache/calcite#943
Project: http://git-wip-us.apache.org/repos/asf/calcite/repo
Commit: http://git-wip-us.apache.org/repos/asf/calcite/commit/847e76cd
Tree: http://git-wip-us.apache.org/repos/asf/calcite/tree/847e76cd
Diff: http://git-wip-us.apache.org/repos/asf/calcite/diff/847e76cd
Branch: refs/heads/master
Commit: 847e76cde2894ea7540749f68669ce2d910c2fa9
Parents: ce47088
Author: Zoltan Haindrich <ki...@rxd.hu>
Authored: Mon Nov 26 15:58:50 2018 +0100
Committer: Julian Hyde <jh...@apache.org>
Committed: Fri Nov 30 20:29:35 2018 -0800
----------------------------------------------------------------------
.../calcite/plan/RexImplicationChecker.java | 4 +-
.../calcite/plan/SubstitutionVisitor.java | 8 +-
.../java/org/apache/calcite/rel/core/Match.java | 2 +-
.../org/apache/calcite/rel/core/Window.java | 13 ++
.../calcite/rel/metadata/RelMdPredicates.java | 137 +++++++++----------
.../apache/calcite/rel/metadata/RelMdUtil.java | 39 +-----
.../calcite/rel/mutable/MutableFilter.java | 5 +-
.../apache/calcite/rel/mutable/MutableJoin.java | 6 +-
.../calcite/rel/mutable/MutableSemiJoin.java | 6 +-
.../rel/rules/AbstractMaterializedViewRule.java | 97 ++++++-------
.../calcite/rel/rules/DateRangeRules.java | 21 ++-
.../rel/rules/JoinPushExpressionsRule.java | 2 +-
.../apache/calcite/rel/rules/PushProjector.java | 39 ++----
.../calcite/rel/rules/ReduceDecimalsRule.java | 8 +-
.../rel/rules/ReduceExpressionsRule.java | 2 +-
.../calcite/rel/rules/SubQueryRemoveRule.java | 2 +-
.../org/apache/calcite/rex/LogicVisitor.java | 2 +-
.../java/org/apache/calcite/rex/RexCall.java | 22 ++-
.../apache/calcite/rex/RexCorrelVariable.java | 12 ++
.../org/apache/calcite/rex/RexDynamicParam.java | 14 ++
.../java/org/apache/calcite/rex/RexNode.java | 13 ++
.../java/org/apache/calcite/rex/RexOver.java | 6 +-
.../apache/calcite/rex/RexProgramBuilder.java | 4 +-
.../org/apache/calcite/rex/RexRangeRef.java | 13 ++
.../org/apache/calcite/rex/RexSimplify.java | 85 ++++++------
.../org/apache/calcite/rex/RexSubQuery.java | 7 +-
.../java/org/apache/calcite/rex/RexUtil.java | 46 +++----
.../org/apache/calcite/rex/RexVariable.java | 10 +-
.../calcite/sql2rel/SqlToRelConverter.java | 16 +--
.../org/apache/calcite/test/RelOptRulesTest.xml | 9 +-
.../calcite/test/SqlToRelConverterTest.xml | 34 ++---
.../elasticsearch/ElasticsearchRules.java | 4 +-
32 files changed, 336 insertions(+), 352 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/plan/RexImplicationChecker.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/plan/RexImplicationChecker.java b/core/src/main/java/org/apache/calcite/plan/RexImplicationChecker.java
index f2b32f2..d769b7e 100644
--- a/core/src/main/java/org/apache/calcite/plan/RexImplicationChecker.java
+++ b/core/src/main/java/org/apache/calcite/plan/RexImplicationChecker.java
@@ -168,7 +168,7 @@ public class RexImplicationChecker {
}
// E.g. "x is null" implies "x is null".
- if (RexUtil.eq(first, second)) {
+ if (first.equals(second)) {
return true;
}
@@ -184,7 +184,7 @@ public class RexImplicationChecker {
final RexNode operand = ((RexCall) second).getOperands().get(0);
final Strong strong = new Strong() {
@Override public boolean isNull(RexNode node) {
- return RexUtil.eq(node, operand)
+ return node.equals(operand)
|| super.isNull(node);
}
};
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/plan/SubstitutionVisitor.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/plan/SubstitutionVisitor.java b/core/src/main/java/org/apache/calcite/plan/SubstitutionVisitor.java
index 4212fae..b30763c 100644
--- a/core/src/main/java/org/apache/calcite/plan/SubstitutionVisitor.java
+++ b/core/src/main/java/org/apache/calcite/plan/SubstitutionVisitor.java
@@ -1362,13 +1362,13 @@ public class SubstitutionVisitor {
/** Builds a shuttle that stores a list of expressions, and can map incoming
* expressions to references to them. */
protected static RexShuttle getRexShuttle(MutableProject target) {
- final Map<String, Integer> map = new HashMap<>();
+ final Map<RexNode, Integer> map = new HashMap<>();
for (RexNode e : target.projects) {
- map.put(e.toString(), map.size());
+ map.put(e, map.size());
}
return new RexShuttle() {
@Override public RexNode visitInputRef(RexInputRef ref) {
- final Integer integer = map.get(ref.getName());
+ final Integer integer = map.get(ref);
if (integer != null) {
return new RexInputRef(integer, ref.getType());
}
@@ -1376,7 +1376,7 @@ public class SubstitutionVisitor {
}
@Override public RexNode visitCall(RexCall call) {
- final Integer integer = map.get(call.toString());
+ final Integer integer = map.get(call);
if (integer != null) {
return new RexInputRef(integer, call.getType());
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/core/Match.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/core/Match.java b/core/src/main/java/org/apache/calcite/rel/core/Match.java
index d2c170e..742fa81 100644
--- a/core/src/main/java/org/apache/calcite/rel/core/Match.java
+++ b/core/src/main/java/org/apache/calcite/rel/core/Match.java
@@ -277,7 +277,7 @@ public abstract class Match extends SingleRel {
}
boolean update = true;
for (RexMRAggCall rex : set) {
- if (rex.toString().equals(aggCall.toString())) {
+ if (rex.equals(aggCall)) {
update = false;
break;
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/core/Window.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/core/Window.java b/core/src/main/java/org/apache/calcite/rel/core/Window.java
index 186f7d3..013e7cc 100644
--- a/core/src/main/java/org/apache/calcite/rel/core/Window.java
+++ b/core/src/main/java/org/apache/calcite/rel/core/Window.java
@@ -47,6 +47,7 @@ import com.google.common.collect.ImmutableList;
import java.util.AbstractList;
import java.util.List;
+import java.util.Objects;
/**
* A relational expression representing a set of window aggregates.
@@ -361,6 +362,18 @@ public abstract class Window extends SingleRel {
this.distinct = distinct;
}
+ /** {@inheritDoc}
+ *
+ * <p>Override {@link RexCall}, defining equality based on identity.
+ */
+ @Override public boolean equals(Object obj) {
+ return this == obj;
+ }
+
+ @Override public int hashCode() {
+ return Objects.hash(digest, ordinal, distinct);
+ }
+
@Override public RexCall clone(RelDataType type, List<RexNode> operands) {
throw new UnsupportedOperationException();
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/metadata/RelMdPredicates.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/metadata/RelMdPredicates.java b/core/src/main/java/org/apache/calcite/rel/metadata/RelMdPredicates.java
index 985464c..a7993cb 100644
--- a/core/src/main/java/org/apache/calcite/rel/metadata/RelMdPredicates.java
+++ b/core/src/main/java/org/apache/calcite/rel/metadata/RelMdPredicates.java
@@ -59,9 +59,9 @@ import org.apache.calcite.util.mapping.Mappings;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.Iterables;
-import com.google.common.collect.Lists;
import java.util.ArrayList;
+import java.util.Arrays;
import java.util.BitSet;
import java.util.Collections;
import java.util.HashMap;
@@ -69,7 +69,6 @@ import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
-import java.util.Map.Entry;
import java.util.Objects;
import java.util.Set;
import java.util.SortedMap;
@@ -358,58 +357,56 @@ public class RelMdPredicates
* Infers predicates for a Union.
*/
public RelOptPredicateList getPredicates(Union union, RelMetadataQuery mq) {
- RexBuilder rexBuilder = union.getCluster().getRexBuilder();
+ final RexBuilder rexBuilder = union.getCluster().getRexBuilder();
- Map<String, RexNode> finalPreds = new HashMap<>();
- List<RexNode> finalResidualPreds = new ArrayList<>();
- for (int i = 0; i < union.getInputs().size(); i++) {
- RelNode input = union.getInputs().get(i);
- RelOptPredicateList info = mq.getPulledUpPredicates(input);
+ Set<RexNode> finalPredicates = new HashSet<>();
+ final List<RexNode> finalResidualPredicates = new ArrayList<>();
+ for (Ord<RelNode> input : Ord.zip(union.getInputs())) {
+ RelOptPredicateList info = mq.getPulledUpPredicates(input.e);
if (info.pulledUpPredicates.isEmpty()) {
return RelOptPredicateList.EMPTY;
}
- Map<String, RexNode> preds = new HashMap<>();
- List<RexNode> residualPreds = new ArrayList<>();
+ final Set<RexNode> predicates = new HashSet<>();
+ final List<RexNode> residualPredicates = new ArrayList<>();
for (RexNode pred : info.pulledUpPredicates) {
- final String predDigest = pred.toString();
- if (i == 0) {
- preds.put(predDigest, pred);
+ if (input.i == 0) {
+ predicates.add(pred);
continue;
}
- if (finalPreds.containsKey(predDigest)) {
- preds.put(predDigest, pred);
+ if (finalPredicates.contains(pred)) {
+ predicates.add(pred);
} else {
- residualPreds.add(pred);
+ residualPredicates.add(pred);
}
}
- // Add new residual preds
- finalResidualPreds.add(RexUtil.composeConjunction(rexBuilder, residualPreds));
+ // Add new residual predicates
+ finalResidualPredicates.add(RexUtil.composeConjunction(rexBuilder, residualPredicates));
// Add those that are not part of the final set to residual
- for (Entry<String, RexNode> e : finalPreds.entrySet()) {
- if (!preds.containsKey(e.getKey())) {
+ for (RexNode e : finalPredicates) {
+ if (!predicates.contains(e)) {
// This node was in previous union inputs, but it is not in this one
- for (int j = 0; j < i; j++) {
- finalResidualPreds.set(j,
+ for (int j = 0; j < input.i; j++) {
+ finalResidualPredicates.set(j,
RexUtil.composeConjunction(rexBuilder,
- Lists.newArrayList(finalResidualPreds.get(j), e.getValue())));
+ Arrays.asList(finalResidualPredicates.get(j), e)));
}
}
}
- // Final preds
- finalPreds = preds;
+ // Final predicates
+ finalPredicates = predicates;
}
- List<RexNode> preds = new ArrayList<>(finalPreds.values());
+ final List<RexNode> predicates = new ArrayList<>(finalPredicates);
final RelOptCluster cluster = union.getCluster();
final RexExecutor executor =
Util.first(cluster.getPlanner().getExecutor(), RexUtil.EXECUTOR);
- final RelOptPredicateList predicates = RelOptPredicateList.EMPTY;
- RexNode disjPred = new RexSimplify(rexBuilder, predicates, executor)
- .simplifyOrs(finalResidualPreds);
- if (!disjPred.isAlwaysTrue()) {
- preds.add(disjPred);
+ RexNode disjunctivePredicate =
+ new RexSimplify(rexBuilder, RelOptPredicateList.EMPTY, executor)
+ .simplifyOrs(finalResidualPredicates);
+ if (!disjunctivePredicate.isAlwaysTrue()) {
+ predicates.add(disjunctivePredicate);
}
- return RelOptPredicateList.of(rexBuilder, preds);
+ return RelOptPredicateList.of(rexBuilder, predicates);
}
/**
@@ -479,20 +476,20 @@ public class RelMdPredicates
final ImmutableBitSet rightFieldsBitSet;
final ImmutableBitSet allFieldsBitSet;
SortedMap<Integer, BitSet> equivalence;
- final Map<String, ImmutableBitSet> exprFields;
- final Set<String> allExprDigests;
- final Set<String> equalityPredicates;
+ final Map<RexNode, ImmutableBitSet> exprFields;
+ final Set<RexNode> allExprs;
+ final Set<RexNode> equalityPredicates;
final RexNode leftChildPredicates;
final RexNode rightChildPredicates;
final RexSimplify simplify;
JoinConditionBasedPredicateInference(Join joinRel,
- RexNode lPreds, RexNode rPreds, RexSimplify simplify) {
- this(joinRel, joinRel instanceof SemiJoin, lPreds, rPreds, simplify);
+ RexNode leftPredicates, RexNode rightPredicates, RexSimplify simplify) {
+ this(joinRel, joinRel instanceof SemiJoin, leftPredicates, rightPredicates, simplify);
}
private JoinConditionBasedPredicateInference(Join joinRel, boolean isSemiJoin,
- RexNode lPreds, RexNode rPreds, RexSimplify simplify) {
+ RexNode leftPredicates, RexNode rightPredicates, RexSimplify simplify) {
super();
this.joinRel = joinRel;
this.isSemiJoin = isSemiJoin;
@@ -508,35 +505,35 @@ public class RelMdPredicates
nSysFields + nFieldsLeft + nFieldsRight);
exprFields = new HashMap<>();
- allExprDigests = new HashSet<>();
+ allExprs = new HashSet<>();
- if (lPreds == null) {
+ if (leftPredicates == null) {
leftChildPredicates = null;
} else {
Mappings.TargetMapping leftMapping = Mappings.createShiftMapping(
nSysFields + nFieldsLeft, nSysFields, 0, nFieldsLeft);
- leftChildPredicates = lPreds.accept(
+ leftChildPredicates = leftPredicates.accept(
new RexPermuteInputsShuttle(leftMapping, joinRel.getInput(0)));
- allExprDigests.add(leftChildPredicates.toString());
+ allExprs.add(leftChildPredicates);
for (RexNode r : RelOptUtil.conjunctions(leftChildPredicates)) {
- exprFields.put(r.toString(), RelOptUtil.InputFinder.bits(r));
- allExprDigests.add(r.toString());
+ exprFields.put(r, RelOptUtil.InputFinder.bits(r));
+ allExprs.add(r);
}
}
- if (rPreds == null) {
+ if (rightPredicates == null) {
rightChildPredicates = null;
} else {
Mappings.TargetMapping rightMapping = Mappings.createShiftMapping(
nSysFields + nFieldsLeft + nFieldsRight,
nSysFields + nFieldsLeft, 0, nFieldsRight);
- rightChildPredicates = rPreds.accept(
+ rightChildPredicates = rightPredicates.accept(
new RexPermuteInputsShuttle(rightMapping, joinRel.getInput(1)));
- allExprDigests.add(rightChildPredicates.toString());
+ allExprs.add(rightChildPredicates);
for (RexNode r : RelOptUtil.conjunctions(rightChildPredicates)) {
- exprFields.put(r.toString(), RelOptUtil.InputFinder.bits(r));
- allExprDigests.add(r.toString());
+ exprFields.put(r, RelOptUtil.InputFinder.bits(r));
+ allExprs.add(r);
}
}
@@ -555,8 +552,7 @@ public class RelMdPredicates
compose(rexBuilder, ImmutableList.of(joinRel.getCondition())));
final EquivalenceFinder eF = new EquivalenceFinder();
- new ArrayList<>(
- Lists.transform(exprs, input -> input.accept(eF)));
+ exprs.forEach(input -> input.accept(eF));
equivalence = BitSets.closure(equivalence);
}
@@ -577,12 +573,12 @@ public class RelMdPredicates
public RelOptPredicateList inferPredicates(
boolean includeEqualityInference) {
final List<RexNode> inferredPredicates = new ArrayList<>();
- final Set<String> allExprDigests = new HashSet<>(this.allExprDigests);
+ final Set<RexNode> allExprs = new HashSet<>(this.allExprs);
final JoinRelType joinType = joinRel.getJoinType();
switch (joinType) {
case INNER:
case LEFT:
- infer(leftChildPredicates, allExprDigests, inferredPredicates,
+ infer(leftChildPredicates, allExprs, inferredPredicates,
includeEqualityInference,
joinType == JoinRelType.LEFT ? rightFieldsBitSet
: allFieldsBitSet);
@@ -591,7 +587,7 @@ public class RelMdPredicates
switch (joinType) {
case INNER:
case RIGHT:
- infer(rightChildPredicates, allExprDigests, inferredPredicates,
+ infer(rightChildPredicates, allExprs, inferredPredicates,
includeEqualityInference,
joinType == JoinRelType.RIGHT ? leftFieldsBitSet
: allFieldsBitSet);
@@ -659,12 +655,12 @@ public class RelMdPredicates
return rightChildPredicates;
}
- private void infer(RexNode predicates, Set<String> allExprsDigests,
+ private void infer(RexNode predicates, Set<RexNode> allExprs,
List<RexNode> inferredPredicates, boolean includeEqualityInference,
ImmutableBitSet inferringFields) {
for (RexNode r : RelOptUtil.conjunctions(predicates)) {
if (!includeEqualityInference
- && equalityPredicates.contains(r.toString())) {
+ && equalityPredicates.contains(r)) {
continue;
}
for (Mapping m : mappings(r)) {
@@ -676,33 +672,31 @@ public class RelMdPredicates
// some duplicates in in result pulledUpPredicates
RexNode simplifiedTarget =
simplify.simplifyFilterPredicates(RelOptUtil.conjunctions(tr));
- if (checkTarget(inferringFields, allExprsDigests, tr)
- && checkTarget(inferringFields, allExprsDigests, simplifiedTarget)) {
+ if (checkTarget(inferringFields, allExprs, tr)
+ && checkTarget(inferringFields, allExprs, simplifiedTarget)) {
inferredPredicates.add(simplifiedTarget);
- allExprsDigests.add(simplifiedTarget.toString());
+ allExprs.add(simplifiedTarget);
}
}
}
}
Iterable<Mapping> mappings(final RexNode predicate) {
- return () -> {
- ImmutableBitSet fields = exprFields.get(predicate.toString());
- if (fields.cardinality() == 0) {
- return Collections.emptyIterator();
- }
- return new ExprsItr(fields);
- };
+ final ImmutableBitSet fields = exprFields.get(predicate);
+ if (fields.cardinality() == 0) {
+ return Collections.emptyList();
+ }
+ return () -> new ExprsItr(fields);
}
private boolean checkTarget(ImmutableBitSet inferringFields,
- Set<String> allExprsDigests, RexNode tr) {
+ Set<RexNode> allExprs, RexNode tr) {
return inferringFields.contains(RelOptUtil.InputFinder.bits(tr))
- && !allExprsDigests.contains(tr.toString())
+ && !allExprs.contains(tr)
&& !isAlwaysTrue(tr);
}
- private void equivalent(int p1, int p2) {
+ private void markAsEquivalent(int p1, int p2) {
BitSet b = equivalence.get(p1);
b.set(p2);
@@ -728,9 +722,8 @@ public class RelMdPredicates
int lPos = pos(call.getOperands().get(0));
int rPos = pos(call.getOperands().get(1));
if (lPos != -1 && rPos != -1) {
- JoinConditionBasedPredicateInference.this.equivalent(lPos, rPos);
- JoinConditionBasedPredicateInference.this.equalityPredicates
- .add(call.toString());
+ markAsEquivalent(lPos, rPos);
+ equalityPredicates.add(call);
}
}
return null;
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/metadata/RelMdUtil.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/metadata/RelMdUtil.java b/core/src/main/java/org/apache/calcite/rel/metadata/RelMdUtil.java
index 6229f4e..73cae72 100644
--- a/core/src/main/java/org/apache/calcite/rel/metadata/RelMdUtil.java
+++ b/core/src/main/java/org/apache/calcite/rel/metadata/RelMdUtil.java
@@ -49,7 +49,7 @@ import com.google.common.collect.ImmutableList;
import java.math.BigDecimal;
import java.util.ArrayList;
-import java.util.HashSet;
+import java.util.LinkedHashSet;
import java.util.List;
import java.util.Set;
@@ -433,20 +433,9 @@ public class RelMdUtil {
RexBuilder rexBuilder,
RexNode pred1,
RexNode pred2) {
- final List<RexNode> unionList = new ArrayList<>();
- final Set<String> strings = new HashSet<>();
-
- for (RexNode rex : RelOptUtil.conjunctions(pred1)) {
- if (strings.add(rex.toString())) {
- unionList.add(rex);
- }
- }
- for (RexNode rex2 : RelOptUtil.conjunctions(pred2)) {
- if (strings.add(rex2.toString())) {
- unionList.add(rex2);
- }
- }
-
+ final Set<RexNode> unionList = new LinkedHashSet<>();
+ unionList.addAll(RelOptUtil.conjunctions(pred1));
+ unionList.addAll(RelOptUtil.conjunctions(pred2));
return RexUtil.composeConjunction(rexBuilder, unionList, true);
}
@@ -463,23 +452,9 @@ public class RelMdUtil {
RexBuilder rexBuilder,
RexNode pred1,
RexNode pred2) {
- final List<RexNode> list1 = RelOptUtil.conjunctions(pred1);
- final List<RexNode> list2 = RelOptUtil.conjunctions(pred2);
- final List<RexNode> minusList = new ArrayList<>();
-
- for (RexNode rex1 : list1) {
- boolean add = true;
- for (RexNode rex2 : list2) {
- if (rex2.toString().compareTo(rex1.toString()) == 0) {
- add = false;
- break;
- }
- }
- if (add) {
- minusList.add(rex1);
- }
- }
-
+ final List<RexNode> minusList =
+ new ArrayList<>(RelOptUtil.conjunctions(pred1));
+ minusList.removeAll(RelOptUtil.conjunctions(pred2));
return RexUtil.composeConjunction(rexBuilder, minusList, true);
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/mutable/MutableFilter.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/mutable/MutableFilter.java b/core/src/main/java/org/apache/calcite/rel/mutable/MutableFilter.java
index 787487f..ef9f8d7 100644
--- a/core/src/main/java/org/apache/calcite/rel/mutable/MutableFilter.java
+++ b/core/src/main/java/org/apache/calcite/rel/mutable/MutableFilter.java
@@ -43,13 +43,12 @@ public class MutableFilter extends MutableSingleRel {
@Override public boolean equals(Object obj) {
return obj == this
|| obj instanceof MutableFilter
- && condition.toString().equals(
- ((MutableFilter) obj).condition.toString())
+ && condition.equals(((MutableFilter) obj).condition)
&& input.equals(((MutableFilter) obj).input);
}
@Override public int hashCode() {
- return Objects.hash(input, condition.toString());
+ return Objects.hash(input, condition);
}
@Override public StringBuilder digest(StringBuilder buf) {
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/mutable/MutableJoin.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/mutable/MutableJoin.java b/core/src/main/java/org/apache/calcite/rel/mutable/MutableJoin.java
index 09d5a1c..0a49c8c 100644
--- a/core/src/main/java/org/apache/calcite/rel/mutable/MutableJoin.java
+++ b/core/src/main/java/org/apache/calcite/rel/mutable/MutableJoin.java
@@ -66,8 +66,7 @@ public class MutableJoin extends MutableBiRel {
return obj == this
|| obj instanceof MutableJoin
&& joinType == ((MutableJoin) obj).joinType
- && condition.toString().equals(
- ((MutableJoin) obj).condition.toString())
+ && condition.equals(((MutableJoin) obj).condition)
&& Objects.equals(variablesSet,
((MutableJoin) obj).variablesSet)
&& left.equals(((MutableJoin) obj).left)
@@ -75,8 +74,7 @@ public class MutableJoin extends MutableBiRel {
}
@Override public int hashCode() {
- return Objects.hash(left, right,
- condition.toString(), joinType, variablesSet);
+ return Objects.hash(left, right, condition, joinType, variablesSet);
}
@Override public StringBuilder digest(StringBuilder buf) {
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/mutable/MutableSemiJoin.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/mutable/MutableSemiJoin.java b/core/src/main/java/org/apache/calcite/rel/mutable/MutableSemiJoin.java
index c2e81b7..5806696 100644
--- a/core/src/main/java/org/apache/calcite/rel/mutable/MutableSemiJoin.java
+++ b/core/src/main/java/org/apache/calcite/rel/mutable/MutableSemiJoin.java
@@ -61,8 +61,7 @@ public class MutableSemiJoin extends MutableBiRel {
@Override public boolean equals(Object obj) {
return obj == this
|| obj instanceof MutableSemiJoin
- && condition.toString().equals(
- ((MutableSemiJoin) obj).condition.toString())
+ && condition.equals(((MutableSemiJoin) obj).condition)
&& leftKeys.equals(((MutableSemiJoin) obj).leftKeys)
&& rightKeys.equals(((MutableSemiJoin) obj).rightKeys)
&& left.equals(((MutableSemiJoin) obj).left)
@@ -70,8 +69,7 @@ public class MutableSemiJoin extends MutableBiRel {
}
@Override public int hashCode() {
- return Objects.hash(left, right,
- condition.toString(), leftKeys, rightKeys);
+ return Objects.hash(left, right, condition, leftKeys, rightKeys);
}
@Override public StringBuilder digest(StringBuilder buf) {
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/rules/AbstractMaterializedViewRule.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/rules/AbstractMaterializedViewRule.java b/core/src/main/java/org/apache/calcite/rel/rules/AbstractMaterializedViewRule.java
index 89e444a..7eedc93 100644
--- a/core/src/main/java/org/apache/calcite/rel/rules/AbstractMaterializedViewRule.java
+++ b/core/src/main/java/org/apache/calcite/rel/rules/AbstractMaterializedViewRule.java
@@ -1359,7 +1359,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
}
// Generate result rewriting
- List<String> additionalViewExprs = new ArrayList<>();
+ final List<RexNode> additionalViewExprs = new ArrayList<>();
Mapping rewritingMapping = null;
RelNode result = relBuilder.push(input).build();
// We create view expressions that will be used in a Project on top of the
@@ -1389,7 +1389,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
RexNode targetNode = rollupNodes.get(
targetIdx - viewInputFieldCount - viewInputDifferenceViewFieldCount);
// We need to rollup this expression
- final Multimap<String, Integer> exprsLineage = ArrayListMultimap.create();
+ final Multimap<RexNode, Integer> exprsLineage = ArrayListMultimap.create();
final ImmutableBitSet refs = RelOptUtil.InputFinder.bits(targetNode);
for (int childTargetIdx : refs) {
added = false;
@@ -1398,10 +1398,10 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
if (!n.isA(SqlKind.INPUT_REF)) {
continue;
}
- int ref = ((RexInputRef) n).getIndex();
+ final int ref = ((RexInputRef) n).getIndex();
if (ref == childTargetIdx) {
exprsLineage.put(
- new RexInputRef(childTargetIdx, targetNode.getType()).toString(), k);
+ new RexInputRef(ref, targetNode.getType()), k);
added = true;
}
}
@@ -1414,7 +1414,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
groupSetB.set(inputViewExprs.size());
rewritingMapping.set(inputViewExprs.size(), i);
additionalViewExprs.add(
- new RexInputRef(targetIdx, targetNode.getType()).toString());
+ new RexInputRef(targetIdx, targetNode.getType()));
// We need to create the rollup expression
inputViewExprs.add(
shuttleReferences(rexBuilder, targetNode, exprsLineage));
@@ -1536,12 +1536,12 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
topRowType = queryAggregate.getRowType();
}
// Available in view.
- final Multimap<String, Integer> viewExprs = ArrayListMultimap.create();
+ final Multimap<RexNode, Integer> viewExprs = ArrayListMultimap.create();
int numberViewExprs = 0;
for (RexNode viewExpr : topViewProject.getChildExps()) {
- viewExprs.put(viewExpr.toString(), numberViewExprs++);
+ viewExprs.put(viewExpr, numberViewExprs++);
}
- for (String additionalViewExpr : additionalViewExprs) {
+ for (RexNode additionalViewExpr : additionalViewExprs) {
viewExprs.put(additionalViewExpr, numberViewExprs++);
}
final List<RexNode> rewrittenExprs = new ArrayList<>(topExprs.size());
@@ -1587,7 +1587,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
Multimap<Integer, Integer> m = ArrayListMultimap.create();
Map<RexTableInputRef, Set<RexTableInputRef>> equivalenceClassesMap =
sourceEC.getEquivalenceClassesMap();
- Multimap<String, Integer> exprsLineage = ArrayListMultimap.create();
+ Multimap<RexNode, Integer> exprsLineage = ArrayListMultimap.create();
List<RexNode> timestampExprs = new ArrayList<>();
for (int i = 0; i < target.getRowType().getFieldCount(); i++) {
Set<RexNode> s = mq.getExpressionLineage(target, rexBuilder.makeInputRef(target, i));
@@ -1604,7 +1604,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
simplified,
tableMapping.inverse(),
equivalenceClassesMap);
- exprsLineage.put(expr.toString(), i);
+ exprsLineage.put(expr, i);
SqlTypeName sqlTypeName = expr.getType().getSqlTypeName();
if (sqlTypeName == SqlTypeName.TIMESTAMP
|| sqlTypeName == SqlTypeName.TIMESTAMP_WITH_LOCAL_TIME_ZONE) {
@@ -1633,7 +1633,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
// can try to find a match
final RexNode simplified =
simplify.simplifyUnknownAsFalse(ceilExpr);
- exprsLineage.put(simplified.toString(),
+ exprsLineage.put(simplified,
target.getRowType().getFieldCount() + additionalExprs.size() - 1);
}
// FLOOR
@@ -1651,7 +1651,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
// can try to find a match
final RexNode simplified =
simplify.simplifyUnknownAsFalse(floorExpr);
- exprsLineage.put(simplified.toString(),
+ exprsLineage.put(simplified,
target.getRowType().getFieldCount() + additionalExprs.size() - 1);
}
}
@@ -1670,7 +1670,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
final RexNode simplified = simplify.simplifyUnknownAsFalse(e);
RexNode targetExpr = RexUtil.swapColumnReferences(rexBuilder,
simplified, equivalenceClassesMap);
- Collection<Integer> c = exprsLineage.get(targetExpr.toString());
+ final Collection<Integer> c = exprsLineage.get(targetExpr);
if (!c.isEmpty()) {
for (Integer j : c) {
m.put(i, j);
@@ -2010,8 +2010,8 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
parentTRef.getTable().getRowType().getFieldList().get(uniqueKeyPos).getType());
if (!foreignKeyColumnType.isNullable()
&& sourceEC.getEquivalenceClassesMap().containsKey(uniqueKeyColumnRef)
- && sourceEC.getEquivalenceClassesMap().get(uniqueKeyColumnRef).contains(
- foreignKeyColumnRef)) {
+ && sourceEC.getEquivalenceClassesMap().get(uniqueKeyColumnRef)
+ .contains(foreignKeyColumnRef)) {
equiColumns.put(foreignKeyColumnRef, uniqueKeyColumnRef);
} else {
canBeRewritten = false;
@@ -2310,8 +2310,8 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
BiMap<RelTableRef, RelTableRef> tableMapping,
EquivalenceClasses ec,
List<RexNode> nodeExprs) {
- Map<String, Integer> exprsLineage = new HashMap<>();
- Map<String, Integer> exprsLineageLosslessCasts = new HashMap<>();
+ final Map<RexNode, Integer> exprsLineage = new HashMap<>();
+ final Map<RexNode, Integer> exprsLineageLosslessCasts = new HashMap<>();
for (int i = 0; i < nodeExprs.size(); i++) {
final Set<RexNode> s = mq.getExpressionLineage(node, nodeExprs.get(i));
if (s == null) {
@@ -2325,12 +2325,12 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
// mapping, then we take first element from the corresponding equivalence class
final RexNode e = RexUtil.swapTableColumnReferences(rexBuilder,
s.iterator().next(), tableMapping, ec.getEquivalenceClassesMap());
- exprsLineage.put(e.toString(), i);
+ exprsLineage.put(e, i);
if (RexUtil.isLosslessCast(e)) {
- exprsLineageLosslessCasts.put(((RexCall) e).getOperands().get(0).toString(), i);
+ exprsLineageLosslessCasts.put(((RexCall) e).getOperands().get(0), i);
}
}
- return NodeLineage.of(exprsLineage, exprsLineageLosslessCasts);
+ return new NodeLineage(exprsLineage, exprsLineageLosslessCasts);
}
/**
@@ -2344,8 +2344,8 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
BiMap<RelTableRef, RelTableRef> tableMapping,
EquivalenceClasses ec,
List<RexNode> nodeExprs) {
- Map<String, Integer> exprsLineage = new HashMap<>();
- Map<String, Integer> exprsLineageLosslessCasts = new HashMap<>();
+ final Map<RexNode, Integer> exprsLineage = new HashMap<>();
+ final Map<RexNode, Integer> exprsLineageLosslessCasts = new HashMap<>();
for (int i = 0; i < nodeExprs.size(); i++) {
final Set<RexNode> s = mq.getExpressionLineage(node, nodeExprs.get(i));
if (s == null) {
@@ -2354,17 +2354,17 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
}
// We only support project - filter - join, thus it should map to
// a single expression
- assert s.size() == 1;
+ final RexNode node2 = Iterables.getOnlyElement(s);
// Rewrite expr. First we take first element from the corresponding equivalence class,
// then we swap the table references following the table mapping
- final RexNode e = RexUtil.swapColumnTableReferences(
- rexBuilder, s.iterator().next(), ec.getEquivalenceClassesMap(), tableMapping);
- exprsLineage.put(e.toString(), i);
+ final RexNode e = RexUtil.swapColumnTableReferences(rexBuilder, node2,
+ ec.getEquivalenceClassesMap(), tableMapping);
+ exprsLineage.put(e, i);
if (RexUtil.isLosslessCast(e)) {
- exprsLineageLosslessCasts.put(((RexCall) e).getOperands().get(0).toString(), i);
+ exprsLineageLosslessCasts.put(((RexCall) e).getOperands().get(0), i);
}
}
- return NodeLineage.of(exprsLineage, exprsLineageLosslessCasts);
+ return new NodeLineage(exprsLineage, exprsLineageLosslessCasts);
}
/**
@@ -2392,12 +2392,12 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
}
private RexNode replace(RexNode e) {
- Integer pos = nodeLineage.exprsLineage.get(e.toString());
+ Integer pos = nodeLineage.exprsLineage.get(e);
if (pos != null) {
// Found it
return rexBuilder.makeInputRef(node, pos);
}
- pos = nodeLineage.exprsLineageLosslessCasts.get(e.toString());
+ pos = nodeLineage.exprsLineageLosslessCasts.get(e);
if (pos != null) {
// Found it
return rexBuilder.makeCast(
@@ -2436,29 +2436,29 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
}
/**
- * Replaces all the possible subexpressions by input references
+ * Replaces all the possible sub-expressions by input references
* to the input node.
*/
private static RexNode shuttleReferences(final RexBuilder rexBuilder,
- final RexNode expr, final Multimap<String, Integer> exprsLineage) {
+ final RexNode expr, final Multimap<RexNode, Integer> exprsLineage) {
return shuttleReferences(rexBuilder, expr,
exprsLineage, null, null);
}
/**
- * Replaces all the possible subexpressions by input references
+ * Replaces all the possible sub-expressions by input references
* to the input node. If available, it uses the rewriting mapping
* to change the position to reference. Takes the reference type
* from the input node.
*/
private static RexNode shuttleReferences(final RexBuilder rexBuilder,
- final RexNode expr, final Multimap<String, Integer> exprsLineage,
+ final RexNode expr, final Multimap<RexNode, Integer> exprsLineage,
final RelNode node, final Mapping rewritingMapping) {
try {
RexShuttle visitor =
new RexShuttle() {
@Override public RexNode visitTableInputRef(RexTableInputRef ref) {
- Collection<Integer> c = exprsLineage.get(ref.toString());
+ Collection<Integer> c = exprsLineage.get(ref);
if (c.isEmpty()) {
// Cannot map expression
throw Util.FoundOne.NULL;
@@ -2478,7 +2478,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
}
@Override public RexNode visitInputRef(RexInputRef inputRef) {
- Collection<Integer> c = exprsLineage.get(inputRef.toString());
+ Collection<Integer> c = exprsLineage.get(inputRef);
if (c.isEmpty()) {
// Cannot map expression
throw Util.FoundOne.NULL;
@@ -2498,7 +2498,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
}
@Override public RexNode visitCall(final RexCall call) {
- Collection<Integer> c = exprsLineage.get(call.toString());
+ Collection<Integer> c = exprsLineage.get(call);
if (c.isEmpty()) {
// Cannot map expression
return super.visitCall(call);
@@ -2612,28 +2612,21 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule {
}
}
- /**
- * Class to encapsulate expression lineage details
- */
+ /** Expression lineage details. */
private static class NodeLineage {
- private final Map<String, Integer> exprsLineage;
- private final Map<String, Integer> exprsLineageLosslessCasts;
+ private final Map<RexNode, Integer> exprsLineage;
+ private final Map<RexNode, Integer> exprsLineageLosslessCasts;
- private NodeLineage(Map<String, Integer> exprsLineage,
- Map<String, Integer> exprsLineageLosslessCasts) {
- this.exprsLineage = Collections.unmodifiableMap(exprsLineage);
- this.exprsLineageLosslessCasts = Collections.unmodifiableMap(exprsLineageLosslessCasts);
- }
-
- protected static NodeLineage of(
- Map<String, Integer> exprsLineage, Map<String, Integer> exprsLineageLosslessCasts) {
- return new NodeLineage(exprsLineage, exprsLineageLosslessCasts);
+ private NodeLineage(Map<RexNode, Integer> exprsLineage,
+ Map<RexNode, Integer> exprsLineageLosslessCasts) {
+ this.exprsLineage = ImmutableMap.copyOf(exprsLineage);
+ this.exprsLineageLosslessCasts =
+ ImmutableMap.copyOf(exprsLineageLosslessCasts);
}
}
/** Edge for graph */
private static class Edge extends DefaultEdge {
-
final Multimap<RexTableInputRef, RexTableInputRef> equiColumns =
ArrayListMultimap.create();
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/rules/DateRangeRules.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/rules/DateRangeRules.java b/core/src/main/java/org/apache/calcite/rel/rules/DateRangeRules.java
index e9a968e..8d2337f 100644
--- a/core/src/main/java/org/apache/calcite/rel/rules/DateRangeRules.java
+++ b/core/src/main/java/org/apache/calcite/rel/rules/DateRangeRules.java
@@ -158,7 +158,7 @@ public abstract class DateRangeRules {
timeUnits = ImmutableSortedSet.<TimeUnitRange>naturalOrder()
.addAll(timeUnits).add(TimeUnitRange.YEAR).build();
}
- final Map<String, RangeSet<Calendar>> operandRanges = new HashMap<>();
+ final Map<RexNode, RangeSet<Calendar>> operandRanges = new HashMap<>();
for (TimeUnitRange timeUnit : timeUnits) {
e = e.accept(
new ExtractShuttle(rexBuilder, timeUnit, operandRanges, timeUnits,
@@ -183,7 +183,7 @@ public abstract class DateRangeRules {
.unwrap(CalciteConnectionConfig.class).timeZone();
final RexNode condition =
replaceTimeUnits(rexBuilder, filter.getCondition(), timeZone);
- if (RexUtil.eq(condition, filter.getCondition())) {
+ if (condition.equals(filter.getCondition())) {
return;
}
final RelBuilder relBuilder =
@@ -238,14 +238,14 @@ public abstract class DateRangeRules {
static class ExtractShuttle extends RexShuttle {
private final RexBuilder rexBuilder;
private final TimeUnitRange timeUnit;
- private final Map<String, RangeSet<Calendar>> operandRanges;
+ private final Map<RexNode, RangeSet<Calendar>> operandRanges;
private final Deque<RexCall> calls = new ArrayDeque<>();
private final ImmutableSortedSet<TimeUnitRange> timeUnitRanges;
private final String timeZone;
@VisibleForTesting
ExtractShuttle(RexBuilder rexBuilder, TimeUnitRange timeUnit,
- Map<String, RangeSet<Calendar>> operandRanges,
+ Map<RexNode, RangeSet<Calendar>> operandRanges,
ImmutableSortedSet<TimeUnitRange> timeUnitRanges, String timeZone) {
this.rexBuilder = Objects.requireNonNull(rexBuilder);
this.timeUnit = Objects.requireNonNull(timeUnit);
@@ -332,8 +332,7 @@ public abstract class DateRangeRules {
if (timeUnit == TimeUnitRange.YEAR) {
return true;
}
- final RangeSet<Calendar> calendarRangeSet =
- operandRanges.get(operand.toString());
+ final RangeSet<Calendar> calendarRangeSet = operandRanges.get(operand);
if (calendarRangeSet == null || calendarRangeSet.isEmpty()) {
return false;
}
@@ -361,7 +360,7 @@ public abstract class DateRangeRules {
//noinspection unchecked
return (List<RexNode>) exprs;
}
- final Map<String, RangeSet<Calendar>> save =
+ final Map<RexNode, RangeSet<Calendar>> save =
ImmutableMap.copyOf(operandRanges);
final ImmutableList.Builder<RexNode> clonedOperands =
ImmutableList.builder();
@@ -400,7 +399,7 @@ public abstract class DateRangeRules {
RexNode compareExtract(SqlKind comparison, RexNode operand,
RexLiteral literal) {
- RangeSet<Calendar> rangeSet = operandRanges.get(operand.toString());
+ RangeSet<Calendar> rangeSet = operandRanges.get(operand);
if (rangeSet == null) {
rangeSet = ImmutableRangeSet.<Calendar>of().complement();
}
@@ -439,7 +438,7 @@ public abstract class DateRangeRules {
}
// Intersect old range set with new.
s2.removeAll(rangeSet.complement());
- operandRanges.put(operand.toString(), ImmutableRangeSet.copyOf(s2));
+ operandRanges.put(operand, ImmutableRangeSet.copyOf(s2));
final List<RexNode> nodes = new ArrayList<>();
for (Range<Calendar> r : s2.asRanges()) {
nodes.add(toRex(operand, r));
@@ -569,7 +568,7 @@ public abstract class DateRangeRules {
private RexNode compareFloorCeil(SqlKind comparison, RexNode operand,
RexLiteral timeLiteral, TimeUnitRange timeUnit, boolean floor) {
- RangeSet<Calendar> rangeSet = operandRanges.get(operand.toString());
+ RangeSet<Calendar> rangeSet = operandRanges.get(operand);
if (rangeSet == null) {
rangeSet = ImmutableRangeSet.<Calendar>of().complement();
}
@@ -581,7 +580,7 @@ public abstract class DateRangeRules {
s2.add(range);
// Intersect old range set with new.
s2.removeAll(rangeSet.complement());
- operandRanges.put(operand.toString(), ImmutableRangeSet.copyOf(s2));
+ operandRanges.put(operand, ImmutableRangeSet.copyOf(s2));
if (range.isEmpty()) {
return rexBuilder.makeLiteral(false);
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/rules/JoinPushExpressionsRule.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/rules/JoinPushExpressionsRule.java b/core/src/main/java/org/apache/calcite/rel/rules/JoinPushExpressionsRule.java
index 4fb33e5..923809f 100644
--- a/core/src/main/java/org/apache/calcite/rel/rules/JoinPushExpressionsRule.java
+++ b/core/src/main/java/org/apache/calcite/rel/rules/JoinPushExpressionsRule.java
@@ -61,7 +61,7 @@ public class JoinPushExpressionsRule extends RelOptRule {
// If the join is the same, we bail out
if (newJoin instanceof Join) {
final RexNode newCondition = ((Join) newJoin).getCondition();
- if (join.getCondition().toString().equals(newCondition.toString())) {
+ if (join.getCondition().equals(newCondition)) {
return;
}
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/rules/PushProjector.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/rules/PushProjector.java b/core/src/main/java/org/apache/calcite/rel/rules/PushProjector.java
index e0d6b71..e34a4a8 100644
--- a/core/src/main/java/org/apache/calcite/rel/rules/PushProjector.java
+++ b/core/src/main/java/org/apache/calcite/rel/rules/PushProjector.java
@@ -700,11 +700,15 @@ public class PushProjector {
final ImmutableBitSet exprArgs = RelOptUtil.InputFinder.bits(call);
if (exprArgs.cardinality() > 0) {
if (leftFields.contains(exprArgs) && isStrong(exprArgs, call)) {
- addExpr(preserveLeft, call);
+ if (!preserveLeft.contains(call)) {
+ preserveLeft.add(call);
+ }
return true;
} else if (rightFields.contains(exprArgs) && isStrong(exprArgs, call)) {
assert preserveRight != null;
- addExpr(preserveRight, call);
+ if (!preserveRight.contains(call)) {
+ preserveRight.add(call);
+ }
return true;
}
}
@@ -721,22 +725,6 @@ public class PushProjector {
return null;
}
- /**
- * Adds an expression to a list if the same expression isn't already in
- * the list. Expressions are identical if their digests are the same.
- *
- * @param exprList current list of expressions
- * @param newExpr new expression to be added
- */
- private void addExpr(List<RexNode> exprList, RexNode newExpr) {
- String newExprString = newExpr.toString();
- for (RexNode expr : exprList) {
- if (newExprString.compareTo(expr.toString()) == 0) {
- return;
- }
- }
- exprList.add(newExpr);
- }
}
/**
@@ -804,13 +792,13 @@ public class PushProjector {
int adjust1,
List<RexNode> rexList2,
int adjust2) {
- int match = findExprInList(rex, rexList1);
+ int match = rexList1.indexOf(rex);
if (match >= 0) {
return match + adjust1;
}
if (rexList2 != null) {
- match = findExprInList(rex, rexList2);
+ match = rexList2.indexOf(rex);
if (match >= 0) {
return match + adjust2;
}
@@ -818,17 +806,6 @@ public class PushProjector {
return -1;
}
-
- private int findExprInList(RexNode rex, List<RexNode> rexList) {
- int match = 0;
- for (RexNode rexElement : rexList) {
- if (rexElement.toString().compareTo(rex.toString()) == 0) {
- return match;
- }
- match++;
- }
- return -1;
- }
}
/**
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/rules/ReduceDecimalsRule.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/rules/ReduceDecimalsRule.java b/core/src/main/java/org/apache/calcite/rel/rules/ReduceDecimalsRule.java
index 1242d51..c8dd509 100644
--- a/core/src/main/java/org/apache/calcite/rel/rules/ReduceDecimalsRule.java
+++ b/core/src/main/java/org/apache/calcite/rel/rules/ReduceDecimalsRule.java
@@ -122,8 +122,8 @@ public class ReduceDecimalsRule extends RelOptRule {
* longs.
*/
public class DecimalShuttle extends RexShuttle {
- private final Map<Pair<String, String>, RexNode> irreducible;
- private final Map<Pair<String, String>, RexNode> results;
+ private final Map<Pair<RexNode, String>, RexNode> irreducible;
+ private final Map<Pair<RexNode, String>, RexNode> results;
private final ExpanderMap expanderMap;
public DecimalShuttle(RexBuilder rexBuilder) {
@@ -173,7 +173,7 @@ public class ReduceDecimalsRule extends RelOptRule {
* Registers node so it will not be computed again
*/
private void register(RexNode node, RexNode reducedNode) {
- Pair<String, String> key = RexUtil.makeKey(node);
+ Pair<RexNode, String> key = RexUtil.makeKey(node);
if (node == reducedNode) {
irreducible.put(key, reducedNode);
} else {
@@ -185,7 +185,7 @@ public class ReduceDecimalsRule extends RelOptRule {
* Lookup registered node
*/
private RexNode lookup(RexNode node) {
- Pair<String, String> key = RexUtil.makeKey(node);
+ Pair<RexNode, String> key = RexUtil.makeKey(node);
if (irreducible.get(key) != null) {
return node;
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/rules/ReduceExpressionsRule.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/rules/ReduceExpressionsRule.java b/core/src/main/java/org/apache/calcite/rel/rules/ReduceExpressionsRule.java
index 741d083..50823f4 100644
--- a/core/src/main/java/org/apache/calcite/rel/rules/ReduceExpressionsRule.java
+++ b/core/src/main/java/org/apache/calcite/rel/rules/ReduceExpressionsRule.java
@@ -547,7 +547,7 @@ public abstract class ReduceExpressionsRule extends RelOptRule {
boolean simplified = false;
for (int i = 0; i < expList.size(); i++) {
RexNode expr2 = simplifier.apply(expList.get(i));
- if (!expr2.toString().equals(expList.get(i).toString())) {
+ if (!expr2.equals(expList.get(i))) {
expList.set(i, expr2);
simplified = true;
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rel/rules/SubQueryRemoveRule.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/rules/SubQueryRemoveRule.java b/core/src/main/java/org/apache/calcite/rel/rules/SubQueryRemoveRule.java
index b993184..9eebeb3 100644
--- a/core/src/main/java/org/apache/calcite/rel/rules/SubQueryRemoveRule.java
+++ b/core/src/main/java/org/apache/calcite/rel/rules/SubQueryRemoveRule.java
@@ -599,7 +599,7 @@ public abstract class SubQueryRemoveRule extends RelOptRule {
}
@Override public RexNode visitSubQuery(RexSubQuery subQuery) {
- return RexUtil.eq(subQuery, this.subQuery) ? replacement : subQuery;
+ return subQuery.equals(this.subQuery) ? replacement : subQuery;
}
}
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/LogicVisitor.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/LogicVisitor.java b/core/src/main/java/org/apache/calcite/rex/LogicVisitor.java
index f632e94..7d4f494 100644
--- a/core/src/main/java/org/apache/calcite/rex/LogicVisitor.java
+++ b/core/src/main/java/org/apache/calcite/rex/LogicVisitor.java
@@ -115,7 +115,7 @@ public class LogicVisitor implements RexBiVisitor<Logic, Logic> {
}
private Logic end(RexNode node, Logic arg) {
- if (RexUtil.eq(node, seek)) {
+ if (node.equals(seek)) {
logicCollection.add(arg);
}
return arg;
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexCall.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexCall.java b/core/src/main/java/org/apache/calcite/rex/RexCall.java
index d2c4ac2..26b095d 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexCall.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexCall.java
@@ -26,6 +26,7 @@ import com.google.common.collect.ImmutableList;
import java.util.List;
import java.util.Objects;
+import javax.annotation.Nonnull;
/**
* An expression formed by a call to an operator with zero or more expressions
@@ -65,8 +66,8 @@ public class RexCall extends RexNode {
//~ Methods ----------------------------------------------------------------
- protected String computeDigest(boolean withType) {
- StringBuilder sb = new StringBuilder(op.getName());
+ protected @Nonnull String computeDigest(boolean withType) {
+ final StringBuilder sb = new StringBuilder(op.getName());
if ((operands.size() == 0)
&& (op.getSyntax() == SqlSyntax.FUNCTION_ID)) {
// Don't print params for empty arg list. For example, we want
@@ -77,8 +78,7 @@ public class RexCall extends RexNode {
if (i > 0) {
sb.append(", ");
}
- RexNode operand = operands.get(i);
- sb.append(operand.toString());
+ sb.append(operands.get(i));
}
sb.append(")");
}
@@ -92,13 +92,13 @@ public class RexCall extends RexNode {
return sb.toString();
}
- public String toString() {
+ @Override public final @Nonnull String toString() {
// This data race is intentional
String localDigest = digest;
if (localDigest == null) {
localDigest = computeDigest(
isA(SqlKind.CAST) || isA(SqlKind.NEW_SPECIFICATION));
- digest = localDigest;
+ digest = Objects.requireNonNull(localDigest);
}
return localDigest;
}
@@ -173,6 +173,16 @@ public class RexCall extends RexNode {
public RexCall clone(RelDataType type, List<RexNode> operands) {
return new RexCall(type, op, operands);
}
+
+ @Override public boolean equals(Object obj) {
+ return obj == this
+ || obj instanceof RexCall
+ && toString().equals(obj.toString());
+ }
+
+ @Override public int hashCode() {
+ return toString().hashCode();
+ }
}
// End RexCall.java
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexCorrelVariable.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexCorrelVariable.java b/core/src/main/java/org/apache/calcite/rex/RexCorrelVariable.java
index 750a97b..a16b30d 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexCorrelVariable.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexCorrelVariable.java
@@ -54,6 +54,18 @@ public class RexCorrelVariable extends RexVariable {
@Override public SqlKind getKind() {
return SqlKind.CORREL_VARIABLE;
}
+
+ @Override public boolean equals(Object obj) {
+ return this == obj
+ || obj instanceof RexCorrelVariable
+ && digest.equals(((RexCorrelVariable) obj).digest)
+ && type.equals(((RexCorrelVariable) obj).type)
+ && id.equals(((RexCorrelVariable) obj).id);
+ }
+
+ @Override public int hashCode() {
+ return Objects.hash(digest, type, id);
+ }
}
// End RexCorrelVariable.java
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexDynamicParam.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexDynamicParam.java b/core/src/main/java/org/apache/calcite/rex/RexDynamicParam.java
index 6bbd692..7e92d4a 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexDynamicParam.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexDynamicParam.java
@@ -19,6 +19,8 @@ package org.apache.calcite.rex;
import org.apache.calcite.rel.type.RelDataType;
import org.apache.calcite.sql.SqlKind;
+import java.util.Objects;
+
/**
* Dynamic parameter reference in a row-expression.
*/
@@ -59,6 +61,18 @@ public class RexDynamicParam extends RexVariable {
public <R, P> R accept(RexBiVisitor<R, P> visitor, P arg) {
return visitor.visitDynamicParam(this, arg);
}
+
+ @Override public boolean equals(Object obj) {
+ return this == obj
+ || obj instanceof RexDynamicParam
+ && digest.equals(((RexDynamicParam) obj).digest)
+ && type.equals(((RexDynamicParam) obj).type)
+ && index == ((RexDynamicParam) obj).index;
+ }
+
+ @Override public int hashCode() {
+ return Objects.hash(digest, type, index);
+ }
}
// End RexDynamicParam.java
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexNode.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexNode.java b/core/src/main/java/org/apache/calcite/rex/RexNode.java
index 95df460..ca382c0 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexNode.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexNode.java
@@ -96,6 +96,19 @@ public abstract class RexNode {
* {@link RexBiVisitor#visitInputRef(RexInputRef, Object)} visitXxx} method.
*/
public abstract <R, P> R accept(RexBiVisitor<R, P> visitor, P arg);
+
+ /** {@inheritDoc}
+ *
+ * <p>Every node must implement {@link #equals} based on its content
+ */
+ @Override public abstract boolean equals(Object obj);
+
+ /** {@inheritDoc}
+ *
+ * <p>Every node must implement {@link #hashCode} consistent with
+ * {@link #equals}
+ */
+ @Override public abstract int hashCode();
}
// End RexNode.java
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexOver.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexOver.java b/core/src/main/java/org/apache/calcite/rex/RexOver.java
index fe7f7d9..7737ccb 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexOver.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexOver.java
@@ -26,6 +26,7 @@ import com.google.common.base.Preconditions;
import java.util.List;
import java.util.Objects;
+import javax.annotation.Nonnull;
/**
* Call to an aggregate function over a window.
@@ -88,7 +89,7 @@ public class RexOver extends RexCall {
return distinct;
}
- @Override protected String computeDigest(boolean withType) {
+ @Override protected @Nonnull String computeDigest(boolean withType) {
final StringBuilder sb = new StringBuilder(op.getName());
sb.append("(");
if (distinct) {
@@ -98,8 +99,7 @@ public class RexOver extends RexCall {
if (i > 0) {
sb.append(", ");
}
- RexNode operand = operands.get(i);
- sb.append(operand.toString());
+ sb.append(operands.get(i));
}
sb.append(")");
if (withType) {
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexProgramBuilder.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexProgramBuilder.java b/core/src/main/java/org/apache/calcite/rex/RexProgramBuilder.java
index f871b9d..9feb711 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexProgramBuilder.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexProgramBuilder.java
@@ -43,7 +43,7 @@ public class RexProgramBuilder {
private final RexBuilder rexBuilder;
private final RelDataType inputRowType;
private final List<RexNode> exprList = new ArrayList<>();
- private final Map<Pair<String, String>, RexLocalRef> exprMap =
+ private final Map<Pair<RexNode, String>, RexLocalRef> exprMap =
new HashMap<>();
private final List<RexLocalRef> localRefList = new ArrayList<>();
private final List<RexLocalRef> projectRefList = new ArrayList<>();
@@ -329,7 +329,7 @@ public class RexProgramBuilder {
expr = simplify.simplifyPreservingType(expr);
RexLocalRef ref;
- final Pair<String, String> key;
+ final Pair<RexNode, String> key;
if (expr instanceof RexLocalRef) {
key = null;
ref = (RexLocalRef) expr;
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexRangeRef.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexRangeRef.java b/core/src/main/java/org/apache/calcite/rex/RexRangeRef.java
index 04aa277..97d5e46 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexRangeRef.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexRangeRef.java
@@ -18,6 +18,8 @@ package org.apache.calcite.rex;
import org.apache.calcite.rel.type.RelDataType;
+import java.util.Objects;
+
/**
* Reference to a range of columns.
*
@@ -74,6 +76,17 @@ public class RexRangeRef extends RexNode {
public <R, P> R accept(RexBiVisitor<R, P> visitor, P arg) {
return visitor.visitRangeRef(this, arg);
}
+
+ @Override public boolean equals(Object obj) {
+ return this == obj
+ || obj instanceof RexRangeRef
+ && type.equals(((RexRangeRef) obj).type)
+ && offset == ((RexRangeRef) obj).offset;
+ }
+
+ @Override public int hashCode() {
+ return Objects.hash(type, offset);
+ }
}
// End RexRangeRef.java
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexSimplify.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexSimplify.java b/core/src/main/java/org/apache/calcite/rex/RexSimplify.java
index a8e95e9..f78a90c 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexSimplify.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexSimplify.java
@@ -300,7 +300,7 @@ public class RexSimplify {
// Simplify "x <op> x"
final RexNode o0 = operands.get(0);
final RexNode o1 = operands.get(1);
- if (RexUtil.eq(o0, o1)
+ if (o0.equals(o1)
&& (unknownAs == FALSE
|| (!o0.getType().isNullable()
&& !o1.getType().isNullable()))) {
@@ -514,7 +514,7 @@ public class RexSimplify {
for (RexNode p : predicates.pulledUpPredicates) {
IsPredicate pred = IsPredicate.of(p);
- if (pred == null || !a.toString().equals(pred.ref.toString())) {
+ if (pred == null || !a.equals(pred.ref)) {
continue;
}
if (kind == pred.kind) {
@@ -649,12 +649,12 @@ public class RexSimplify {
}
private RexNode simplifyCoalesce(RexCall call) {
- final Set<String> digests = new HashSet<>();
+ final Set<RexNode> operandSet = new HashSet<>();
final List<RexNode> operands = new ArrayList<>();
for (RexNode operand : call.getOperands()) {
operand = simplify(operand, UNKNOWN);
if (!RexUtil.isNull(operand)
- && digests.add(operand.toString())) {
+ && operandSet.add(operand)) {
operands.add(operand);
}
if (!operand.getType().isNullable()) {
@@ -699,7 +699,7 @@ public class RexSimplify {
// create new branch
if (lastBranch != null) {
- if (lastBranch.value.toString().equals(newValue.toString())
+ if (lastBranch.value.equals(newValue)
&& isSafeExpression(newCond)) {
// in this case, last branch and new branch have the same conclusion,
// hence we create a new composite condition and we do not add it to
@@ -809,7 +809,7 @@ public class RexSimplify {
}
@Override public String toString() {
- return new StringBuilder(cond.toString()).append(" => ").append(value).toString();
+ return cond + " => " + value;
}
/** Given "CASE WHEN p1 THEN v1 ... ELSE e END"
@@ -1120,14 +1120,15 @@ public class RexSimplify {
return simplify(terms.get(0), FALSE);
}
// Try to simplify the expression
- final Multimap<String, Pair<String, RexNode>> equalityTerms = ArrayListMultimap.create();
- final Map<String, Pair<Range<C>, List<RexNode>>> rangeTerms =
+ final Multimap<RexNode, Pair<RexNode, RexNode>> equalityTerms =
+ ArrayListMultimap.create();
+ final Map<RexNode, Pair<Range<C>, List<RexNode>>> rangeTerms =
new HashMap<>();
- final Map<String, String> equalityConstantTerms = new HashMap<>();
- final Set<String> negatedTerms = new HashSet<>();
- final Set<String> nullOperands = new HashSet<>();
+ final Map<RexNode, RexLiteral> equalityConstantTerms = new HashMap<>();
+ final Set<RexNode> negatedTerms = new HashSet<>();
+ final Set<RexNode> nullOperands = new HashSet<>();
final Set<RexNode> notNullOperands = new LinkedHashSet<>();
- final Set<String> comparedOperands = new HashSet<>();
+ final Set<RexNode> comparedOperands = new HashSet<>();
// Add the predicates from the source to the range terms.
for (RexNode predicate : predicates.pulledUpPredicates) {
@@ -1173,19 +1174,19 @@ public class RexSimplify {
case LESS_THAN_OR_EQUAL:
case GREATER_THAN_OR_EQUAL:
RexCall call = (RexCall) term;
- RexNode left = call.getOperands().get(0);
- comparedOperands.add(left.toString());
+ final RexNode left = call.getOperands().get(0);
+ comparedOperands.add(left);
// if it is a cast, we include the inner reference
if (left.getKind() == SqlKind.CAST) {
RexCall leftCast = (RexCall) left;
- comparedOperands.add(leftCast.getOperands().get(0).toString());
+ comparedOperands.add(leftCast.getOperands().get(0));
}
- RexNode right = call.getOperands().get(1);
- comparedOperands.add(right.toString());
+ final RexNode right = call.getOperands().get(1);
+ comparedOperands.add(right);
// if it is a cast, we include the inner reference
if (right.getKind() == SqlKind.CAST) {
RexCall rightCast = (RexCall) right;
- comparedOperands.add(rightCast.getOperands().get(0).toString());
+ comparedOperands.add(rightCast.getOperands().get(0));
}
final Comparison comparison = Comparison.of(term);
// Check for comparison with null values
@@ -1198,15 +1199,15 @@ public class RexSimplify {
// and hence it can be evaluated to FALSE
if (term.getKind() == SqlKind.EQUALS) {
if (comparison != null) {
- final String literal = comparison.literal.toString();
- final String prevLiteral =
- equalityConstantTerms.put(comparison.ref.toString(), literal);
+ final RexLiteral literal = comparison.literal;
+ final RexLiteral prevLiteral =
+ equalityConstantTerms.put(comparison.ref, literal);
if (prevLiteral != null && !literal.equals(prevLiteral)) {
return rexBuilder.makeLiteral(false);
}
} else if (RexUtil.isReferenceOrAccess(left, true)
&& RexUtil.isReferenceOrAccess(right, true)) {
- equalityTerms.put(left.toString(), Pair.of(right.toString(), term));
+ equalityTerms.put(left, Pair.of(right, term));
}
}
// Assume the expression a > 5 is part of a Filter condition.
@@ -1216,10 +1217,10 @@ public class RexSimplify {
// Observe that for creating the inverted term we invert the list of operands.
RexNode negatedTerm = RexUtil.negate(rexBuilder, call);
if (negatedTerm != null) {
- negatedTerms.add(negatedTerm.toString());
+ negatedTerms.add(negatedTerm);
RexNode invertNegatedTerm = RexUtil.invert(rexBuilder, (RexCall) negatedTerm);
if (invertNegatedTerm != null) {
- negatedTerms.add(invertNegatedTerm.toString());
+ negatedTerms.add(invertNegatedTerm);
}
}
// Remove terms that are implied by predicates on the input,
@@ -1243,10 +1244,10 @@ public class RexSimplify {
}
break;
case IN:
- comparedOperands.add(((RexCall) term).operands.get(0).toString());
+ comparedOperands.add(((RexCall) term).operands.get(0));
break;
case BETWEEN:
- comparedOperands.add(((RexCall) term).operands.get(1).toString());
+ comparedOperands.add(((RexCall) term).operands.get(1));
break;
case IS_NOT_NULL:
notNullOperands.add(((RexCall) term).getOperands().get(0));
@@ -1254,7 +1255,7 @@ public class RexSimplify {
--i;
break;
case IS_NULL:
- nullOperands.add(((RexCall) term).getOperands().get(0).toString());
+ nullOperands.add(((RexCall) term).getOperands().get(0));
}
}
// If one column should be null and is in a comparison predicate,
@@ -1266,14 +1267,14 @@ public class RexSimplify {
// Check for equality of two refs wrt equality with constants
// Example #1. x=5 AND y=5 AND x=y : x=5 AND y=5
// Example #2. x=5 AND y=6 AND x=y - not satisfiable
- for (String ref1 : equalityTerms.keySet()) {
- final String literal1 = equalityConstantTerms.get(ref1);
+ for (RexNode ref1 : equalityTerms.keySet()) {
+ final RexLiteral literal1 = equalityConstantTerms.get(ref1);
if (literal1 == null) {
continue;
}
- Collection<Pair<String, RexNode>> references = equalityTerms.get(ref1);
- for (Pair<String, RexNode> ref2 : references) {
- final String literal2 = equalityConstantTerms.get(ref2.left);
+ Collection<Pair<RexNode, RexNode>> references = equalityTerms.get(ref1);
+ for (Pair<RexNode, RexNode> ref2 : references) {
+ final RexLiteral literal2 = equalityConstantTerms.get(ref2.left);
if (literal2 == null) {
continue;
}
@@ -1291,7 +1292,7 @@ public class RexSimplify {
//
// Example. IS NOT NULL(x) AND x < 5 : x < 5
for (RexNode operand : notNullOperands) {
- if (!comparedOperands.contains(operand.toString())) {
+ if (!comparedOperands.contains(operand)) {
terms.add(
rexBuilder.makeCall(SqlStdOperatorTable.IS_NOT_NULL, operand));
}
@@ -1303,12 +1304,12 @@ public class RexSimplify {
// Example #1. x AND y AND z AND NOT (x AND y) - not satisfiable
// Example #2. x AND y AND NOT (x AND y) - not satisfiable
// Example #3. x AND y AND NOT (x AND y AND z) - may be satisfiable
- final Set<String> termsSet = new HashSet<>(RexUtil.strings(terms));
+ final Set<RexNode> termsSet = new HashSet<>(terms);
for (RexNode notDisjunction : notTerms) {
if (!RexUtil.isDeterministic(notDisjunction)) {
continue;
}
- final List<String> terms2Set = RexUtil.strings(RelOptUtil.conjunctions(notDisjunction));
+ final List<RexNode> terms2Set = RelOptUtil.conjunctions(notDisjunction);
if (termsSet.containsAll(terms2Set)) {
return rexBuilder.makeLiteral(false);
}
@@ -1320,7 +1321,7 @@ public class RexSimplify {
terms.add(simplify(call, FALSE));
}
// The negated terms: only deterministic expressions
- for (String negatedTerm : negatedTerms) {
+ for (RexNode negatedTerm : negatedTerms) {
if (termsSet.contains(negatedTerm)) {
return rexBuilder.makeLiteral(false);
}
@@ -1673,11 +1674,11 @@ public class RexSimplify {
private static <C extends Comparable<C>> RexNode processRange(
RexBuilder rexBuilder, List<RexNode> terms,
- Map<String, Pair<Range<C>, List<RexNode>>> rangeTerms, RexNode term,
+ Map<RexNode, Pair<Range<C>, List<RexNode>>> rangeTerms, RexNode term,
RexNode ref, C v0, SqlKind comparison) {
- Pair<Range<C>, List<RexNode>> p = rangeTerms.get(ref.toString());
+ Pair<Range<C>, List<RexNode>> p = rangeTerms.get(ref);
if (p == null) {
- rangeTerms.put(ref.toString(),
+ rangeTerms.put(ref,
Pair.of(range(comparison, v0),
(List<RexNode>) ImmutableList.of(term)));
} else {
@@ -1691,7 +1692,7 @@ public class RexSimplify {
// Range is empty, not satisfiable
return rexBuilder.makeLiteral(false);
}
- rangeTerms.put(ref.toString(),
+ rangeTerms.put(ref,
Pair.of(Range.singleton(v0),
(List<RexNode>) ImmutableList.of(term)));
// remove
@@ -1862,7 +1863,7 @@ public class RexSimplify {
}
}
newBounds.add(term);
- rangeTerms.put(ref.toString(),
+ rangeTerms.put(ref,
Pair.of(r, (List<RexNode>) newBounds.build()));
} else if (removeLowerBound) {
ImmutableList.Builder<RexNode> newBounds = ImmutableList.builder();
@@ -1874,7 +1875,7 @@ public class RexSimplify {
}
}
newBounds.add(term);
- rangeTerms.put(ref.toString(),
+ rangeTerms.put(ref,
Pair.of(r, (List<RexNode>) newBounds.build()));
}
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexSubQuery.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexSubQuery.java b/core/src/main/java/org/apache/calcite/rex/RexSubQuery.java
index 05fd176..fceb58e 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexSubQuery.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexSubQuery.java
@@ -30,6 +30,7 @@ import org.apache.calcite.sql.type.SqlTypeName;
import com.google.common.collect.ImmutableList;
import java.util.List;
+import javax.annotation.Nonnull;
/**
* Scalar expression that represents an IN, EXISTS or scalar sub-query.
@@ -108,11 +109,11 @@ public class RexSubQuery extends RexCall {
return visitor.visitSubQuery(this, arg);
}
- @Override protected String computeDigest(boolean withType) {
- StringBuilder sb = new StringBuilder(op.getName());
+ @Override protected @Nonnull String computeDigest(boolean withType) {
+ final StringBuilder sb = new StringBuilder(op.getName());
sb.append("(");
for (RexNode operand : operands) {
- sb.append(operand.toString());
+ sb.append(operand);
sb.append(", ");
}
sb.append("{\n");
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexUtil.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexUtil.java b/core/src/main/java/org/apache/calcite/rex/RexUtil.java
index 2eed8d2..56eabb6 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexUtil.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexUtil.java
@@ -968,8 +968,8 @@ public class RexUtil {
* representation. For example, "10" integer and "10" bigint result in
* different keys.
*/
- public static Pair<String, String> makeKey(RexNode expr) {
- return Pair.of(expr.toString(), expr.getType().getFullTypeString());
+ public static Pair<RexNode, String> makeKey(RexNode expr) {
+ return Pair.of(expr, expr.getType().getFullTypeString());
}
/**
@@ -1054,17 +1054,17 @@ public class RexUtil {
return ImmutableList.of();
}
final ImmutableList.Builder<RexNode> builder = ImmutableList.builder();
- final Set<String> digests = new HashSet<>(); // to eliminate duplicates
+ final Set<RexNode> set = new HashSet<>(); // to eliminate duplicates
for (RexNode node : nodes) {
if (node != null) {
- addAnd(builder, digests, node);
+ addAnd(builder, set, node);
}
}
return builder.build();
}
private static void addAnd(ImmutableList.Builder<RexNode> builder,
- Set<String> digests, RexNode node) {
+ Set<RexNode> digests, RexNode node) {
switch (node.getKind()) {
case AND:
for (RexNode operand : ((RexCall) node).getOperands()) {
@@ -1072,7 +1072,7 @@ public class RexUtil {
}
return;
default:
- if (!node.isAlwaysTrue() && digests.add(node.toString())) {
+ if (!node.isAlwaysTrue() && digests.add(node)) {
builder.add(node);
}
}
@@ -1122,23 +1122,23 @@ public class RexUtil {
return ImmutableList.of();
}
final ImmutableList.Builder<RexNode> builder = ImmutableList.builder();
- final Set<String> digests = new HashSet<>(); // to eliminate duplicates
+ final Set<RexNode> set = new HashSet<>(); // to eliminate duplicates
for (RexNode node : nodes) {
- addOr(builder, digests, node);
+ addOr(builder, set, node);
}
return builder.build();
}
private static void addOr(ImmutableList.Builder<RexNode> builder,
- Set<String> digests, RexNode node) {
+ Set<RexNode> set, RexNode node) {
switch (node.getKind()) {
case OR:
for (RexNode operand : ((RexCall) node).getOperands()) {
- addOr(builder, digests, operand);
+ addOr(builder, set, operand);
}
return;
default:
- if (!node.isAlwaysFalse() && digests.add(node.toString())) {
+ if (!node.isAlwaysFalse() && set.add(node)) {
builder.add(node);
}
}
@@ -1637,7 +1637,7 @@ public class RexUtil {
Iterator<RexNode> iterator = targets.iterator();
while (iterator.hasNext()) {
RexNode next = iterator.next();
- if (eq(next, e)) {
+ if (next.equals(e)) {
++count;
iterator.remove();
}
@@ -1650,6 +1650,7 @@ public class RexUtil {
* <p>This method considers structure, not semantics. 'x < y' is not
* equivalent to 'y > x'.
*/
+ @Deprecated // use e1.equals(e2)
public static boolean eq(RexNode e1, RexNode e2) {
return e1 == e2 || e1.toString().equals(e2.toString());
}
@@ -2071,7 +2072,7 @@ public class RexUtil {
* Walks over expressions and builds a bank of common sub-expressions.
*/
private static class ExpressionNormalizer extends RexVisitorImpl<RexNode> {
- final Map<String, RexNode> mapDigestToExpr = new HashMap<>();
+ final Map<RexNode, RexNode> map = new HashMap<>();
final boolean allowDups;
protected ExpressionNormalizer(boolean allowDups) {
@@ -2080,8 +2081,7 @@ public class RexUtil {
}
protected RexNode register(RexNode expr) {
- final String key = expr.toString();
- final RexNode previous = mapDigestToExpr.put(key, expr);
+ final RexNode previous = map.put(expr, expr);
if (!allowDups && (previous != null)) {
throw new SubExprExistsException(expr);
}
@@ -2089,7 +2089,7 @@ public class RexUtil {
}
protected RexNode lookup(RexNode expr) {
- return mapDigestToExpr.get(expr.toString());
+ return map.get(expr);
}
public RexNode visitInputRef(RexInputRef inputRef) {
@@ -2327,7 +2327,7 @@ public class RexUtil {
return and(pullList(operands));
case OR:
operands = flattenOr(((RexCall) rex).getOperands());
- final Map<String, RexNode> factors = commonFactors(operands);
+ final Map<RexNode, RexNode> factors = commonFactors(operands);
if (factors.isEmpty()) {
return or(operands);
}
@@ -2356,25 +2356,25 @@ public class RexUtil {
return list;
}
- private Map<String, RexNode> commonFactors(List<RexNode> nodes) {
- final Map<String, RexNode> map = new HashMap<>();
+ private Map<RexNode, RexNode> commonFactors(List<RexNode> nodes) {
+ final Map<RexNode, RexNode> map = new HashMap<>();
int i = 0;
for (RexNode node : nodes) {
if (i++ == 0) {
for (RexNode conjunction : RelOptUtil.conjunctions(node)) {
- map.put(conjunction.toString(), conjunction);
+ map.put(conjunction, conjunction);
}
} else {
- map.keySet().retainAll(strings(RelOptUtil.conjunctions(node)));
+ map.keySet().retainAll(RelOptUtil.conjunctions(node));
}
}
return map;
}
- private RexNode removeFactor(Map<String, RexNode> factors, RexNode node) {
+ private RexNode removeFactor(Map<RexNode, RexNode> factors, RexNode node) {
List<RexNode> list = new ArrayList<>();
for (RexNode operand : RelOptUtil.conjunctions(node)) {
- if (!factors.containsKey(operand.toString())) {
+ if (!factors.containsKey(operand)) {
list.add(operand);
}
}
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/rex/RexVariable.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rex/RexVariable.java b/core/src/main/java/org/apache/calcite/rex/RexVariable.java
index 717a569..6a702c0 100644
--- a/core/src/main/java/org/apache/calcite/rex/RexVariable.java
+++ b/core/src/main/java/org/apache/calcite/rex/RexVariable.java
@@ -18,6 +18,8 @@ package org.apache.calcite.rex;
import org.apache.calcite.rel.type.RelDataType;
+import java.util.Objects;
+
/**
* A row-expression which references a field.
*/
@@ -32,11 +34,9 @@ public abstract class RexVariable extends RexNode {
protected RexVariable(
String name,
RelDataType type) {
- assert type != null;
- assert name != null;
- this.name = name;
- this.digest = name;
- this.type = type;
+ this.name = Objects.requireNonNull(name);
+ this.digest = Objects.requireNonNull(name);
+ this.type = Objects.requireNonNull(type);
}
//~ Methods ----------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/main/java/org/apache/calcite/sql2rel/SqlToRelConverter.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/sql2rel/SqlToRelConverter.java b/core/src/main/java/org/apache/calcite/sql2rel/SqlToRelConverter.java
index 9512312..2e58719 100644
--- a/core/src/main/java/org/apache/calcite/sql2rel/SqlToRelConverter.java
+++ b/core/src/main/java/org/apache/calcite/sql2rel/SqlToRelConverter.java
@@ -706,8 +706,8 @@ public class SqlToRelConverter {
final List<Integer> origins = new ArrayList<>();
int dupCount = 0;
for (int i = 0; i < projectExprs.size(); i++) {
- int x = findExpr(projectExprs.get(i), projectExprs, i);
- if (x >= 0) {
+ int x = projectExprs.indexOf(projectExprs.get(i));
+ if (x >= 0 && x < i) {
origins.add(x);
++dupCount;
} else {
@@ -770,16 +770,6 @@ public class SqlToRelConverter {
false);
}
- private int findExpr(RexNode seek, List<RexNode> exprs, int count) {
- for (int i = 0; i < count; i++) {
- RexNode expr = exprs.get(i);
- if (expr.toString().equals(seek.toString())) {
- return i;
- }
- }
- return -1;
- }
-
/**
* Converts a query's ORDER BY clause, if any.
*
@@ -5095,7 +5085,7 @@ public class SqlToRelConverter {
private int lookupOrCreateGroupExpr(RexNode expr) {
int index = 0;
for (RexNode convertedInputExpr : Pair.left(convertedInputExprs)) {
- if (expr.toString().equals(convertedInputExpr.toString())) {
+ if (expr.equals(convertedInputExpr)) {
return index;
}
++index;
http://git-wip-us.apache.org/repos/asf/calcite/blob/847e76cd/core/src/test/resources/org/apache/calcite/test/RelOptRulesTest.xml
----------------------------------------------------------------------
diff --git a/core/src/test/resources/org/apache/calcite/test/RelOptRulesTest.xml b/core/src/test/resources/org/apache/calcite/test/RelOptRulesTest.xml
index ba38082..dd775ff 100644
--- a/core/src/test/resources/org/apache/calcite/test/RelOptRulesTest.xml
+++ b/core/src/test/resources/org/apache/calcite/test/RelOptRulesTest.xml
@@ -5245,9 +5245,9 @@ LogicalAggregate(group=[{0}], EXPR$1=[STDDEV_POP($1)], EXPR$2=[AVG($1)], EXPR$3=
</Resource>
<Resource name="planAfter">
<![CDATA[
-LogicalProject(NAME=[$0], EXPR$1=[CAST(POWER(/(-($1, /(*($2, $2), $3)), $3), 0.5)):INTEGER NOT NULL], EXPR$2=[CAST(/($2, $3)):INTEGER NOT NULL], EXPR$3=[CAST(POWER(/(-($4, /(*($2, $2), $3)), CASE(=($3, 1), null, -($3, 1))), 0.5)):INTEGER NOT NULL], EXPR$4=[CAST(/(-($5, /(*($2, $2), $3)), $3)):INTEGER NOT NULL], EXPR$5=[CAST(/(-($6, /(*($2, $2), $3)), CASE(=($3, 1), null, -($3, 1)))):INTEGER NOT NULL])
- LogicalAggregate(group=[{0}], agg#0=[$SUM0($2)], agg#1=[$SUM0($1)], agg#2=[COUNT()], agg#3=[$SUM0($3)], agg#4=[$SUM0($4)], agg#5=[$SUM0($5)])
- LogicalProject(NAME=[$0], DEPTNO=[$1], $f2=[*($1, $1)], $f3=[*($1, $1)], $f4=[*($1, $1)], $f5=[*($1, $1)])
+LogicalProject(NAME=[$0], EXPR$1=[CAST(POWER(/(-($1, /(*($2, $2), $3)), $3), 0.5)):INTEGER NOT NULL], EXPR$2=[CAST(/($2, $3)):INTEGER NOT NULL], EXPR$3=[CAST(POWER(/(-($1, /(*($2, $2), $3)), CASE(=($3, 1), null, -($3, 1))), 0.5)):INTEGER NOT NULL], EXPR$4=[CAST(/(-($1, /(*($2, $2), $3)), $3)):INTEGER NOT NULL], EXPR$5=[CAST(/(-($1, /(*($2, $2), $3)), CASE(=($3, 1), null, -($3, 1)))):INTEGER NOT NULL])
+ LogicalAggregate(group=[{0}], agg#0=[$SUM0($2)], agg#1=[$SUM0($1)], agg#2=[COUNT()])
+ LogicalProject(NAME=[$0], DEPTNO=[$1], $f2=[*($1, $1)])
LogicalProject(NAME=[$1], DEPTNO=[$0])
LogicalTableScan(table=[[CATALOG, SALES, DEPT]])
]]>
@@ -5775,8 +5775,7 @@ LogicalProject(DEPTNO=[$0], ENAME=[$1])
LogicalProject(DEPTNO=[$9], ENAME=[$1])
LogicalJoin(condition=[=($7, $9)], joinType=[inner])
LogicalTableScan(table=[[CATALOG, SALES, EMP]])
- LogicalFilter(condition=[=($0, 10)])
- LogicalTableScan(table=[[CATALOG, SALES, DEPT]])
+ LogicalTableScan(table=[[CATALOG, SALES, DEPT]])
]]>
</Resource>
</TestCase>