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 2015/08/01 00:42:48 UTC

[11/50] [abbrv] incubator-calcite git commit: [CALCITE-698] For "GROUP BY ()", areColumnsUnique should return true for any key

[CALCITE-698] For "GROUP BY ()", areColumnsUnique should return true for any key


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

Branch: refs/heads/branch-release
Commit: a9625ad7a4166da87a7cdbeb41b4bebf8bf1b18c
Parents: d952efb
Author: Julian Hyde <jh...@apache.org>
Authored: Thu Apr 23 19:06:54 2015 -0700
Committer: Julian Hyde <jh...@apache.org>
Committed: Thu Apr 23 19:06:54 2015 -0700

----------------------------------------------------------------------
 .../rel/metadata/RelMdColumnUniqueness.java     | 13 +---
 .../calcite/rel/metadata/RelMdUniqueKeys.java   | 10 +++
 .../apache/calcite/test/RelMetadataTest.java    | 73 ++++++++++++++++++--
 3 files changed, 78 insertions(+), 18 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/a9625ad7/core/src/main/java/org/apache/calcite/rel/metadata/RelMdColumnUniqueness.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/metadata/RelMdColumnUniqueness.java b/core/src/main/java/org/apache/calcite/rel/metadata/RelMdColumnUniqueness.java
index 34f878e..527ab3f 100644
--- a/core/src/main/java/org/apache/calcite/rel/metadata/RelMdColumnUniqueness.java
+++ b/core/src/main/java/org/apache/calcite/rel/metadata/RelMdColumnUniqueness.java
@@ -246,17 +246,8 @@ public class RelMdColumnUniqueness {
       ImmutableBitSet columns,
       boolean ignoreNulls) {
     // group by keys form a unique key
-    if (rel.getGroupCount() > 0) {
-      ImmutableBitSet groupKey = ImmutableBitSet.range(rel.getGroupCount());
-      return columns.contains(groupKey);
-    } else {
-      // interpret an empty set as asking whether the aggregation is full
-      // table (in which case it returns at most one row);
-      // TODO jvs 1-Sept-2008:  apply this convention consistently
-      // to other relational expressions, as well as to
-      // RelMetadataQuery.getUniqueKeys
-      return columns.isEmpty();
-    }
+    ImmutableBitSet groupKey = ImmutableBitSet.range(rel.getGroupCount());
+    return columns.contains(groupKey);
   }
 
   // Catch-all rule when none of the others apply.

http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/a9625ad7/core/src/main/java/org/apache/calcite/rel/metadata/RelMdUniqueKeys.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/metadata/RelMdUniqueKeys.java b/core/src/main/java/org/apache/calcite/rel/metadata/RelMdUniqueKeys.java
index d6a0275..db6788a 100644
--- a/core/src/main/java/org/apache/calcite/rel/metadata/RelMdUniqueKeys.java
+++ b/core/src/main/java/org/apache/calcite/rel/metadata/RelMdUniqueKeys.java
@@ -24,6 +24,7 @@ import org.apache.calcite.rel.core.Join;
 import org.apache.calcite.rel.core.JoinInfo;
 import org.apache.calcite.rel.core.Project;
 import org.apache.calcite.rel.core.SemiJoin;
+import org.apache.calcite.rel.core.SetOp;
 import org.apache.calcite.rel.core.Sort;
 import org.apache.calcite.rex.RexInputRef;
 import org.apache.calcite.rex.RexNode;
@@ -209,6 +210,15 @@ public class RelMdUniqueKeys {
     return ImmutableSet.of(rel.getGroupSet());
   }
 
+  public Set<ImmutableBitSet> getUniqueKeys(SetOp rel,
+      boolean ignoreNulls) {
+    if (!rel.all) {
+      return ImmutableSet.of(
+          ImmutableBitSet.range(rel.getRowType().getFieldCount()));
+    }
+    return ImmutableSet.of();
+  }
+
   // Catch-all rule when none of the others apply.
   public Set<ImmutableBitSet> getUniqueKeys(RelNode rel, boolean ignoreNulls) {
     // no information available

http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/a9625ad7/core/src/test/java/org/apache/calcite/test/RelMetadataTest.java
----------------------------------------------------------------------
diff --git a/core/src/test/java/org/apache/calcite/test/RelMetadataTest.java b/core/src/test/java/org/apache/calcite/test/RelMetadataTest.java
index b92b549..2c46a9f 100644
--- a/core/src/test/java/org/apache/calcite/test/RelMetadataTest.java
+++ b/core/src/test/java/org/apache/calcite/test/RelMetadataTest.java
@@ -67,6 +67,7 @@ import com.google.common.collect.ImmutableSet;
 import com.google.common.collect.Iterables;
 import com.google.common.collect.Lists;
 
+import org.hamcrest.CoreMatchers;
 import org.hamcrest.Matcher;
 import org.junit.Ignore;
 import org.junit.Test;
@@ -586,6 +587,30 @@ public class RelMetadataTest extends SqlToRelTestBase {
     assertTrue(result == null);
   }
 
+  /** Asserts that {@link RelMetadataQuery#getUniqueKeys(RelNode)}
+   * and {@link RelMetadataQuery#areColumnsUnique(RelNode, ImmutableBitSet)}
+   * return consistent results. */
+  private void assertUniqueConsistent(RelNode rel) {
+    Set<ImmutableBitSet> uniqueKeys = RelMetadataQuery.getUniqueKeys(rel);
+    final ImmutableBitSet allCols =
+        ImmutableBitSet.range(0, rel.getRowType().getFieldCount());
+    for (ImmutableBitSet key : allCols.powerSet()) {
+      Boolean result2 = RelMetadataQuery.areColumnsUnique(rel, key);
+      assertTrue(result2 == null || result2 == isUnique(uniqueKeys, key));
+    }
+  }
+
+  /** Returns whether {@code keys} is unique, that is, whether it or a superset
+   * is in {@code keySets}. */
+  private boolean isUnique(Set<ImmutableBitSet> uniqueKeys, ImmutableBitSet key) {
+    for (ImmutableBitSet uniqueKey : uniqueKeys) {
+      if (key.contains(uniqueKey)) {
+        return true;
+      }
+    }
+    return false;
+  }
+
   /** Test case for
    * <a href="https://issues.apache.org/jira/browse/CALCITE-509">[CALCITE-509]
    * "RelMdColumnUniqueness uses ImmutableBitSet.Builder twice, gets
@@ -593,13 +618,47 @@ public class RelMetadataTest extends SqlToRelTestBase {
   @Test public void testJoinUniqueKeys() {
     RelNode rel = convertSql("select * from emp join dept using (deptno)");
     Set<ImmutableBitSet> result = RelMetadataQuery.getUniqueKeys(rel);
-    assertThat(result.toString(), equalTo("[]"));
-    final ImmutableBitSet allCols =
-        ImmutableBitSet.range(0, rel.getRowType().getFieldCount());
-    for (ImmutableBitSet integers : allCols.powerSet()) {
-      Boolean result2 = RelMetadataQuery.areColumnsUnique(rel, integers);
-      assertTrue(result2 == null || !result2);
-    }
+    assertThat(result.isEmpty(), is(true));
+    assertUniqueConsistent(rel);
+  }
+
+  @Test public void testGroupByEmptyUniqueKeys() {
+    RelNode rel = convertSql("select count(*) from emp");
+    Set<ImmutableBitSet> result = RelMetadataQuery.getUniqueKeys(rel);
+    assertThat(result,
+        CoreMatchers.<Set<ImmutableBitSet>>equalTo(
+            ImmutableSet.of(ImmutableBitSet.of())));
+    assertUniqueConsistent(rel);
+  }
+
+  @Test public void testGroupByEmptyHavingUniqueKeys() {
+    RelNode rel = convertSql("select count(*) from emp where 1 = 1");
+    Set<ImmutableBitSet> result = RelMetadataQuery.getUniqueKeys(rel);
+    assertThat(result,
+        CoreMatchers.<Set<ImmutableBitSet>>equalTo(
+            ImmutableSet.of(ImmutableBitSet.of())));
+    assertUniqueConsistent(rel);
+  }
+
+  @Test public void testGroupBy() {
+    RelNode rel = convertSql("select deptno, count(*), sum(sal) from emp\n"
+            + "group by deptno");
+    Set<ImmutableBitSet> result = RelMetadataQuery.getUniqueKeys(rel);
+    assertThat(result,
+        CoreMatchers.<Set<ImmutableBitSet>>equalTo(
+            ImmutableSet.of(ImmutableBitSet.of(0))));
+    assertUniqueConsistent(rel);
+  }
+
+  @Test public void testUnion() {
+    RelNode rel = convertSql("select deptno from emp\n"
+            + "union\n"
+            + "select deptno from dept");
+    Set<ImmutableBitSet> result = RelMetadataQuery.getUniqueKeys(rel);
+    assertThat(result,
+        CoreMatchers.<Set<ImmutableBitSet>>equalTo(
+            ImmutableSet.of(ImmutableBitSet.of(0))));
+    assertUniqueConsistent(rel);
   }
 
   @Test public void testCustomProvider() {