calcite-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From jcama...@apache.org
Subject [10/11] calcite git commit: [CALCITE-1763] Recognize lossless casts in join/aggregate materialized view rewriting rule
Date Wed, 26 Apr 2017 19:18:44 GMT
[CALCITE-1763] Recognize lossless casts in join/aggregate materialized view rewriting rule


Project: http://git-wip-us.apache.org/repos/asf/calcite/repo
Commit: http://git-wip-us.apache.org/repos/asf/calcite/commit/9a691a7d
Tree: http://git-wip-us.apache.org/repos/asf/calcite/tree/9a691a7d
Diff: http://git-wip-us.apache.org/repos/asf/calcite/diff/9a691a7d

Branch: refs/heads/master
Commit: 9a691a7db88f96f930a4a4609f8aea6df601a909
Parents: a2bd49c
Author: Jesus Camacho Rodriguez <jcamacho@apache.org>
Authored: Wed Apr 26 12:49:24 2017 +0100
Committer: Jesus Camacho Rodriguez <jcamacho@apache.org>
Committed: Wed Apr 26 20:05:03 2017 +0100

----------------------------------------------------------------------
 .../rel/rules/AbstractMaterializedViewRule.java | 52 ++++++++++++--------
 .../calcite/test/MaterializationTest.java       | 27 ++++++++++
 2 files changed, 58 insertions(+), 21 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/calcite/blob/9a691a7d/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 071d9af..576c04c 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
@@ -422,7 +422,7 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule
{
             RelBuilder builder = call.builder();
             builder.push(materialization.tableRel);
             if (!compensationPred.isAlwaysTrue()) {
-              builder.filter(compensationPred);
+              builder.filter(simplify.simplify(compensationPred));
             }
             RelNode result = unify(rexBuilder, builder, builder.build(),
                 topProject, node, topViewProject, viewNode, tableMapping,
@@ -1270,9 +1270,9 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule
{
       Map<RexTableInputRef, Set<RexTableInputRef>> equivalenceClassesMap,
       RelMetadataQuery mq) {
     Map<String, Integer> exprsLineage = new HashMap<>();
+    Map<String, Integer> exprsLineageLosslessCasts = new HashMap<>();
     for (int i = 0; i < viewExprs.size(); i++) {
-      final RexNode e = viewExprs.get(i);
-      final Set<RexNode> s = mq.getExpressionLineage(viewNode, e);
+      final Set<RexNode> s = mq.getExpressionLineage(viewNode, viewExprs.get(i));
       if (s == null) {
         // Next expression
         continue;
@@ -1281,18 +1281,18 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule
{
       // a single expression
       assert s.size() == 1;
       // Rewrite expr to be expressed on query tables
-      exprsLineage.put(
-          RexUtil.swapTableColumnReferences(
-              rexBuilder,
-              s.iterator().next(),
-              tableMapping.inverse(),
-              equivalenceClassesMap).toString(),
-          i);
+      final RexNode e = RexUtil.swapTableColumnReferences(rexBuilder,
+          s.iterator().next(), tableMapping.inverse(), equivalenceClassesMap);
+      exprsLineage.put(e.toString(), i);
+      if (RexUtil.isLosslessCast(e)) {
+        exprsLineageLosslessCasts.put(((RexCall) e).getOperands().get(0).toString(), i);
+      }
     }
 
     List<RexNode> rewrittenExprs = new ArrayList<>(exprs.size());
     for (RexNode expr : exprs) {
-      RexNode rewrittenExpr = replaceWithOriginalReferences(rexBuilder, expr, exprsLineage);
+      RexNode rewrittenExpr = replaceWithOriginalReferences(
+          rexBuilder, viewExprs, expr, exprsLineage, exprsLineageLosslessCasts);
       if (RexUtil.containsTableInputRef(rewrittenExpr) != null) {
         // Some expressions were not present in view output
         return null;
@@ -1367,28 +1367,38 @@ public abstract class AbstractMaterializedViewRule extends RelOptRule
{
    * point to.
    */
   private static RexNode replaceWithOriginalReferences(final RexBuilder rexBuilder,
-      final RexNode expr, final Map<String, Integer> mapping) {
+      final List<RexNode> originalExprs, final RexNode expr, final Map<String, Integer>
mapping,
+      final Map<String, Integer> mappingLosslessCasts) {
     // Currently we allow the following:
     // 1) compensation pred can be directly map to expression
     // 2) all references in compensation pred can be map to expressions
+    // We support bypassing lossless casts.
     RexShuttle visitor =
         new RexShuttle() {
           @Override public RexNode visitCall(RexCall call) {
-            Integer pos = mapping.get(call.toString());
-            if (pos != null) {
-              // Found it
-              return rexBuilder.makeInputRef(call.getType(), pos);
-            }
-            return super.visitCall(call);
+            RexNode rw = replace(call);
+            return rw != null ? rw : super.visitCall(call);
           }
 
           @Override public RexNode visitTableInputRef(RexTableInputRef inputRef) {
-            Integer pos = mapping.get(inputRef.toString());
+            RexNode rw = replace(inputRef);
+            return rw != null ? rw : super.visitTableInputRef(inputRef);
+          }
+
+          private RexNode replace(RexNode e) {
+            Integer pos = mapping.get(e.toString());
             if (pos != null) {
               // Found it
-              return rexBuilder.makeInputRef(inputRef.getType(), pos);
+              return rexBuilder.makeInputRef(e.getType(), pos);
             }
-            return super.visitTableInputRef(inputRef);
+            pos = mappingLosslessCasts.get(e.toString());
+            if (pos != null) {
+              // Found it
+              return rexBuilder.makeCast(
+                  e.getType(), rexBuilder.makeInputRef(
+                      originalExprs.get(pos).getType(), pos));
+            }
+            return null;
           }
         };
     return visitor.apply(expr);

http://git-wip-us.apache.org/repos/asf/calcite/blob/9a691a7d/core/src/test/java/org/apache/calcite/test/MaterializationTest.java
----------------------------------------------------------------------
diff --git a/core/src/test/java/org/apache/calcite/test/MaterializationTest.java b/core/src/test/java/org/apache/calcite/test/MaterializationTest.java
index 54ddaed..7e2c89c 100644
--- a/core/src/test/java/org/apache/calcite/test/MaterializationTest.java
+++ b/core/src/test/java/org/apache/calcite/test/MaterializationTest.java
@@ -1355,6 +1355,33 @@ public class MaterializationTest {
               + "  EnumerableTableScan(table=[[hr, m0]])"));
   }
 
+  @Test public void testJoinMaterialization5() {
+    checkMaterialize(
+      "select cast(\"empid\" as BIGINT) from \"emps\"\n"
+          + "join \"depts\" using (\"deptno\")",
+      "select \"empid\" \"deptno\" from \"emps\"\n"
+          + "join \"depts\" using (\"deptno\") where \"empid\" > 1",
+      HR_FKUK_MODEL,
+      CalciteAssert.checkResultContains(
+          "EnumerableCalc(expr#0=[{inputs}], expr#1=[CAST($t0):JavaType(int) NOT NULL], "
+              + "expr#2=[1], expr#3=[>($t1, $t2)], EXPR$0=[$t1], $condition=[$t3])\n"
+              + "  EnumerableTableScan(table=[[hr, m0]])"));
+  }
+
+  @Test public void testJoinMaterialization6() {
+    checkMaterialize(
+      "select cast(\"empid\" as BIGINT) from \"emps\"\n"
+          + "join \"depts\" using (\"deptno\")",
+      "select \"empid\" \"deptno\" from \"emps\"\n"
+          + "join \"depts\" using (\"deptno\") where \"empid\" = 1",
+      HR_FKUK_MODEL,
+      CalciteAssert.checkResultContains(
+          "EnumerableCalc(expr#0=[{inputs}], expr#1=[CAST($t0):JavaType(int) NOT NULL], "
+              + "expr#2=[CAST($t1):INTEGER NOT NULL], expr#3=[1], expr#4=[=($t2, $t3)], "
+              + "EXPR$0=[$t1], $condition=[$t4])\n"
+              + "  EnumerableTableScan(table=[[hr, m0]])"));
+  }
+
   @Test public void testJoinMaterializationUKFK1() {
     checkMaterialize(
       "select \"a\".\"empid\" \"deptno\" from\n"


Mime
View raw message