You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@calcite.apache.org by ru...@apache.org on 2021/05/27 07:24:36 UTC
[calcite] branch master updated: [CALCITE-4621] SemiJoinRule throws
AssertionError on ANTI join
This is an automated email from the ASF dual-hosted git repository.
rubenql pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/calcite.git
The following commit(s) were added to refs/heads/master by this push:
new cac28e9 [CALCITE-4621] SemiJoinRule throws AssertionError on ANTI join
cac28e9 is described below
commit cac28e95762532538cd3d0dce9e933ef9e4d5228
Author: rubenada <ru...@gmail.com>
AuthorDate: Tue May 25 13:51:45 2021 +0100
[CALCITE-4621] SemiJoinRule throws AssertionError on ANTI join
---
.../org/apache/calcite/rel/rules/SemiJoinRule.java | 10 +++---
.../org/apache/calcite/test/RelOptRulesTest.java | 39 ++++++++++++++++++++++
2 files changed, 45 insertions(+), 4 deletions(-)
diff --git a/core/src/main/java/org/apache/calcite/rel/rules/SemiJoinRule.java b/core/src/main/java/org/apache/calcite/rel/rules/SemiJoinRule.java
index 16422d3..60c9f7a 100644
--- a/core/src/main/java/org/apache/calcite/rel/rules/SemiJoinRule.java
+++ b/core/src/main/java/org/apache/calcite/rel/rules/SemiJoinRule.java
@@ -24,6 +24,7 @@ import org.apache.calcite.rel.RelNode;
import org.apache.calcite.rel.core.Aggregate;
import org.apache.calcite.rel.core.Join;
import org.apache.calcite.rel.core.JoinInfo;
+import org.apache.calcite.rel.core.JoinRelType;
import org.apache.calcite.rel.core.Project;
import org.apache.calcite.rex.RexBuilder;
import org.apache.calcite.rex.RexNode;
@@ -45,8 +46,9 @@ import java.util.List;
public abstract class SemiJoinRule
extends RelRule<SemiJoinRule.Config>
implements TransformationRule {
- private static boolean notGenerateNullsOnLeft(Join join) {
- return !join.getJoinType().generatesNullsOnLeft();
+ private static boolean isJoinTypeSupported(Join join) {
+ final JoinRelType type = join.getJoinType();
+ return type == JoinRelType.INNER || type == JoinRelType.SEMI || type == JoinRelType.LEFT;
}
/**
@@ -170,7 +172,7 @@ public abstract class SemiJoinRule
return withOperandSupplier(b ->
b.operand(projectClass).oneInput(b2 ->
b2.operand(joinClass)
- .predicate(SemiJoinRule::notGenerateNullsOnLeft).inputs(
+ .predicate(SemiJoinRule::isJoinTypeSupported).inputs(
b3 -> b3.operand(RelNode.class).anyInputs(),
b4 -> b4.operand(aggregateClass).anyInputs())))
.as(Config.class);
@@ -219,7 +221,7 @@ public abstract class SemiJoinRule
default Config withOperandFor(Class<Join> joinClass,
Class<Aggregate> aggregateClass) {
return withOperandSupplier(b ->
- b.operand(joinClass).predicate(SemiJoinRule::notGenerateNullsOnLeft).inputs(
+ b.operand(joinClass).predicate(SemiJoinRule::isJoinTypeSupported).inputs(
b2 -> b2.operand(RelNode.class).anyInputs(),
b3 -> b3.operand(aggregateClass).anyInputs()))
.as(Config.class);
diff --git a/core/src/test/java/org/apache/calcite/test/RelOptRulesTest.java b/core/src/test/java/org/apache/calcite/test/RelOptRulesTest.java
index e23e86f..d988d72 100644
--- a/core/src/test/java/org/apache/calcite/test/RelOptRulesTest.java
+++ b/core/src/test/java/org/apache/calcite/test/RelOptRulesTest.java
@@ -5513,6 +5513,45 @@ class RelOptRulesTest extends RelOptTestBase {
assertEquals(planBefore, planAfter);
}
+ /** Test case for
+ * <a href="https://issues.apache.org/jira/browse/CALCITE-4621">[CALCITE-4621]
+ * SemiJoinRule throws AssertionError on ANTI join</a>. */
+ @Test void testJoinToSemiJoinRuleOnAntiJoin() {
+ testSemiJoinRuleOnAntiJoin(CoreRules.JOIN_TO_SEMI_JOIN);
+ }
+
+ /** Test case for
+ * <a href="https://issues.apache.org/jira/browse/CALCITE-4621">[CALCITE-4621]
+ * SemiJoinRule throws AssertionError on ANTI join</a>. */
+ @Test void testProjectToSemiJoinRuleOnAntiJoin() {
+ testSemiJoinRuleOnAntiJoin(CoreRules.PROJECT_TO_SEMI_JOIN);
+ }
+
+ private void testSemiJoinRuleOnAntiJoin(RelOptRule rule) {
+ final RelBuilder relBuilder = RelBuilder.create(RelBuilderTest.config().build());
+ final RelNode input = relBuilder
+ .scan("DEPT")
+ .scan("EMP")
+ .project(relBuilder.field("DEPTNO"))
+ .distinct()
+ .antiJoin(relBuilder
+ .equals(
+ relBuilder.field(2, 0, "DEPTNO"),
+ relBuilder.field(2, 1, "DEPTNO")))
+ .project(relBuilder.field("DNAME"))
+ .build();
+
+ final HepProgram program = new HepProgramBuilder()
+ .addRuleInstance(rule)
+ .build();
+ final HepPlanner hepPlanner = new HepPlanner(program);
+ hepPlanner.setRoot(input);
+ final RelNode output = hepPlanner.findBestExp();
+ final String planBefore = RelOptUtil.toString(input);
+ final String planAfter = RelOptUtil.toString(output);
+ assertEquals(planBefore, planAfter);
+ }
+
@Test void testPushJoinCondDownToProject() {
final String sql = "select d.deptno, e.deptno from sales.dept d, sales.emp e\n"
+ " where d.deptno + 10 = e.deptno * 2";