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/09/02 02:09:44 UTC

[08/18] incubator-calcite git commit: [CALCITE-825] Allow user to specify sort order of an ArrayTable

[CALCITE-825] Allow user to specify sort order of an ArrayTable


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

Branch: refs/heads/master
Commit: 87e7454cf5ba1c1d1a492371e493bfae5445e62e
Parents: a5688ff
Author: Julian Hyde <jh...@apache.org>
Authored: Fri Aug 7 16:16:05 2015 -0700
Committer: Julian Hyde <jh...@apache.org>
Committed: Tue Sep 1 16:17:15 2015 -0700

----------------------------------------------------------------------
 .../calcite/adapter/clone/ArrayTable.java       | 47 +++++++++++---------
 .../calcite/adapter/clone/CloneSchema.java      | 26 ++++++++---
 .../apache/calcite/jdbc/CalciteMetaImpl.java    |  4 +-
 .../org/apache/calcite/jdbc/CalcitePrepare.java | 18 +++++---
 .../materialize/MaterializationService.java     |  1 +
 .../calcite/prepare/CalcitePrepareImpl.java     |  6 +++
 .../org/apache/calcite/prepare/Prepare.java     | 12 +++++
 .../org/apache/calcite/rel/RelCollations.java   | 16 ++++---
 8 files changed, 90 insertions(+), 40 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/87e7454c/core/src/main/java/org/apache/calcite/adapter/clone/ArrayTable.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/adapter/clone/ArrayTable.java b/core/src/main/java/org/apache/calcite/adapter/clone/ArrayTable.java
index b9bdba8..d87165c 100644
--- a/core/src/main/java/org/apache/calcite/adapter/clone/ArrayTable.java
+++ b/core/src/main/java/org/apache/calcite/adapter/clone/ArrayTable.java
@@ -27,7 +27,6 @@ import org.apache.calcite.linq4j.Queryable;
 import org.apache.calcite.linq4j.tree.Primitive;
 import org.apache.calcite.rel.RelCollation;
 import org.apache.calcite.rel.RelCollations;
-import org.apache.calcite.rel.RelFieldCollation;
 import org.apache.calcite.rel.type.RelDataType;
 import org.apache.calcite.rel.type.RelDataTypeFactory;
 import org.apache.calcite.rel.type.RelProtoDataType;
@@ -80,14 +79,7 @@ class ArrayTable extends AbstractQueryableTable implements ScannableTable {
         keys.add(ImmutableBitSet.of(ord.i));
       }
     }
-    final List<RelCollation> collations;
-    if (content.sortField >= 0) {
-      collations = ImmutableList.of(
-          RelCollations.of(new RelFieldCollation(content.sortField)));
-    } else {
-      collations = ImmutableList.of();
-    }
-    return Statistics.of(content.size, keys, collations);
+    return Statistics.of(content.size, keys, content.collations);
   }
 
   public Enumerable<Object[]> scan(DataContext root) {
@@ -111,6 +103,11 @@ class ArrayTable extends AbstractQueryableTable implements ScannableTable {
     };
   }
 
+  @SuppressWarnings("unchecked")
+  private static <T> Pair<Object, T> toPair(Object dataSet) {
+    return (Pair<Object, T>) dataSet;
+  }
+
   /** How a column's values are represented. */
   enum RepresentationType {
     /** Constant. Contains only one value.
@@ -450,16 +447,14 @@ class ArrayTable extends AbstractQueryableTable implements ScannableTable {
     }
 
     public Object permute(Object dataSet, int[] sources) {
-      final Pair<Object, Comparable[]> pair =
-          (Pair<Object, Comparable[]>) dataSet;
+      final Pair<Object, Comparable[]> pair = toPair(dataSet);
       Object codes = pair.left;
       Comparable[] codeValues = pair.right;
       return Pair.of(representation.permute(codes, sources), codeValues);
     }
 
     public Object getObject(Object dataSet, int ordinal) {
-      final Pair<Object, Comparable[]> pair =
-          (Pair<Object, Comparable[]>) dataSet;
+      final Pair<Object, Comparable[]> pair = toPair(dataSet);
       int code = representation.getInt(pair.left, ordinal);
       return pair.right[code];
     }
@@ -469,8 +464,7 @@ class ArrayTable extends AbstractQueryableTable implements ScannableTable {
     }
 
     public int size(Object dataSet) {
-      final Pair<Object, Comparable[]> pair =
-          (Pair<Object, Comparable[]>) dataSet;
+      final Pair<Object, Comparable[]> pair = toPair(dataSet);
       return representation.size(pair.left);
     }
 
@@ -581,22 +575,22 @@ class ArrayTable extends AbstractQueryableTable implements ScannableTable {
     }
 
     public Object getObject(Object dataSet, int ordinal) {
-      Pair<Object, Integer> pair = (Pair<Object, Integer>) dataSet;
+      Pair<Object, Integer> pair = toPair(dataSet);
       return pair.left;
     }
 
     public int getInt(Object dataSet, int ordinal) {
-      Pair<Object, Integer> pair = (Pair<Object, Integer>) dataSet;
+      Pair<Object, Integer> pair = toPair(dataSet);
       return ((Number) pair.left).intValue();
     }
 
     public int size(Object dataSet) {
-      Pair<Object, Integer> pair = (Pair<Object, Integer>) dataSet;
+      Pair<Object, Integer> pair = toPair(dataSet);
       return pair.right;
     }
 
     public String toString(Object dataSet) {
-      Pair<Object, Integer> pair = (Pair<Object, Integer>) dataSet;
+      Pair<Object, Integer> pair = toPair(dataSet);
       return Collections.nCopies(pair.right, pair.left).toString();
     }
   }
@@ -808,12 +802,21 @@ class ArrayTable extends AbstractQueryableTable implements ScannableTable {
   public static class Content {
     private final List<Column> columns;
     private final int size;
-    private final int sortField;
+    private final ImmutableList<RelCollation> collations;
 
-    public Content(List<? extends Column> columns, int size, int sortField) {
+    public Content(List<? extends Column> columns, int size,
+        Iterable<? extends RelCollation> collations) {
       this.columns = ImmutableList.copyOf(columns);
       this.size = size;
-      this.sortField = sortField;
+      this.collations = ImmutableList.copyOf(collations);
+    }
+
+    @Deprecated // to be removed before 2.0
+    public Content(List<? extends Column> columns, int size, int sortField) {
+      this(columns, size,
+          sortField >= 0
+              ? RelCollations.createSingleton(sortField)
+              : ImmutableList.<RelCollation>of());
     }
 
     @SuppressWarnings("unchecked")

http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/87e7454c/core/src/main/java/org/apache/calcite/adapter/clone/CloneSchema.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/adapter/clone/CloneSchema.java b/core/src/main/java/org/apache/calcite/adapter/clone/CloneSchema.java
index 2f996b9..afd3798 100644
--- a/core/src/main/java/org/apache/calcite/adapter/clone/CloneSchema.java
+++ b/core/src/main/java/org/apache/calcite/adapter/clone/CloneSchema.java
@@ -23,6 +23,8 @@ import org.apache.calcite.jdbc.CalciteConnection;
 import org.apache.calcite.linq4j.Enumerable;
 import org.apache.calcite.linq4j.QueryProvider;
 import org.apache.calcite.linq4j.Queryable;
+import org.apache.calcite.rel.RelCollation;
+import org.apache.calcite.rel.RelCollations;
 import org.apache.calcite.rel.type.RelProtoDataType;
 import org.apache.calcite.schema.QueryableTable;
 import org.apache.calcite.schema.Schema;
@@ -34,6 +36,7 @@ import org.apache.calcite.schema.impl.AbstractSchema;
 
 import com.google.common.base.Supplier;
 import com.google.common.base.Suppliers;
+import com.google.common.collect.ImmutableList;
 
 import java.lang.reflect.Type;
 import java.util.LinkedHashMap;
@@ -63,7 +66,7 @@ public class CloneSchema extends AbstractSchema {
   }
 
   @Override protected Map<String, Table> getTableMap() {
-    final Map<String, Table> map = new LinkedHashMap<String, Table>();
+    final Map<String, Table> map = new LinkedHashMap<>();
     for (String name : sourceSchema.getTableNames()) {
       final Table table = sourceSchema.getTable(name);
       if (table instanceof QueryableTable) {
@@ -81,14 +84,22 @@ public class CloneSchema extends AbstractSchema {
         sourceTable.asQueryable(queryProvider, sourceSchema, name);
     final JavaTypeFactory typeFactory =
         ((CalciteConnection) queryProvider).getTypeFactory();
-    return createCloneTable(typeFactory, Schemas.proto(sourceTable), null,
-        queryable);
+    return createCloneTable(typeFactory, Schemas.proto(sourceTable),
+        ImmutableList.<RelCollation>of(), null, queryable);
   }
 
+  @Deprecated // to be removed before 2.0
   public static <T> Table createCloneTable(final JavaTypeFactory typeFactory,
       final RelProtoDataType protoRowType,
       final List<ColumnMetaData.Rep> repList,
       final Enumerable<T> source) {
+    return createCloneTable(typeFactory, protoRowType,
+        ImmutableList.<RelCollation>of(), repList, source);
+  }
+
+  public static <T> Table createCloneTable(final JavaTypeFactory typeFactory,
+      final RelProtoDataType protoRowType, final List<RelCollation> collations,
+      final List<ColumnMetaData.Rep> repList, final Enumerable<T> source) {
     final Type elementType;
     if (source instanceof QueryableTable) {
       elementType = ((QueryableTable) source).getElementType();
@@ -108,10 +119,15 @@ public class CloneSchema extends AbstractSchema {
             new Supplier<ArrayTable.Content>() {
               public ArrayTable.Content get() {
                 final ColumnLoader loader =
-                    new ColumnLoader<T>(typeFactory, source, protoRowType,
+                    new ColumnLoader<>(typeFactory, source, protoRowType,
                         repList);
+                final List<RelCollation> collation2 =
+                    collations.isEmpty()
+                        && loader.sortField >= 0
+                        ? RelCollations.createSingleton(loader.sortField)
+                        : collations;
                 return new ArrayTable.Content(loader.representationValues,
-                    loader.size(), loader.sortField);
+                    loader.size(), collation2);
               }
             }));
   }

http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/87e7454c/core/src/main/java/org/apache/calcite/jdbc/CalciteMetaImpl.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/jdbc/CalciteMetaImpl.java b/core/src/main/java/org/apache/calcite/jdbc/CalciteMetaImpl.java
index 9f8ade3..fabaf26 100644
--- a/core/src/main/java/org/apache/calcite/jdbc/CalciteMetaImpl.java
+++ b/core/src/main/java/org/apache/calcite/jdbc/CalciteMetaImpl.java
@@ -34,6 +34,7 @@ import org.apache.calcite.linq4j.Queryable;
 import org.apache.calcite.linq4j.function.Function1;
 import org.apache.calcite.linq4j.function.Functions;
 import org.apache.calcite.linq4j.function.Predicate1;
+import org.apache.calcite.rel.RelCollation;
 import org.apache.calcite.rel.type.RelDataType;
 import org.apache.calcite.rel.type.RelDataTypeFactory;
 import org.apache.calcite.rel.type.RelDataTypeFactoryImpl;
@@ -195,7 +196,8 @@ public class CalciteMetaImpl extends MetaImpl {
       final CalcitePrepare.CalciteSignature<Object> signature =
           new CalcitePrepare.CalciteSignature<Object>("",
               ImmutableList.<AvaticaParameter>of(), internalParameters, null,
-              columns, cursorFactory, -1, null) {
+              columns, cursorFactory, ImmutableList.<RelCollation>of(), -1,
+              null) {
             @Override public Enumerable<Object> enumerable(
                 DataContext dataContext) {
               return Linq4j.asEnumerable(firstFrame.rows);

http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/87e7454c/core/src/main/java/org/apache/calcite/jdbc/CalcitePrepare.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/jdbc/CalcitePrepare.java b/core/src/main/java/org/apache/calcite/jdbc/CalcitePrepare.java
index 2453f98..fe2f898 100644
--- a/core/src/main/java/org/apache/calcite/jdbc/CalcitePrepare.java
+++ b/core/src/main/java/org/apache/calcite/jdbc/CalcitePrepare.java
@@ -30,6 +30,7 @@ import org.apache.calcite.linq4j.tree.ClassDeclaration;
 import org.apache.calcite.plan.RelOptPlanner;
 import org.apache.calcite.plan.RelOptRule;
 import org.apache.calcite.prepare.CalcitePrepareImpl;
+import org.apache.calcite.rel.RelCollation;
 import org.apache.calcite.rel.RelNode;
 import org.apache.calcite.rel.type.RelDataType;
 import org.apache.calcite.rel.type.RelDataTypeFactory;
@@ -260,19 +261,18 @@ public interface CalcitePrepare {
    * statement directly, without an explicit prepare step. */
   class CalciteSignature<T> extends Meta.Signature {
     @JsonIgnore public final RelDataType rowType;
+    @JsonIgnore private final List<RelCollation> collationList;
     private final long maxRowCount;
     private final Bindable<T> bindable;
 
-    public CalciteSignature(String sql,
-        List<AvaticaParameter> parameterList,
-        Map<String, Object> internalParameters,
-        RelDataType rowType,
-        List<ColumnMetaData> columns,
-        Meta.CursorFactory cursorFactory,
-        long maxRowCount,
+    public CalciteSignature(String sql, List<AvaticaParameter> parameterList,
+        Map<String, Object> internalParameters, RelDataType rowType,
+        List<ColumnMetaData> columns, Meta.CursorFactory cursorFactory,
+        List<RelCollation> collationList, long maxRowCount,
         Bindable<T> bindable) {
       super(columns, sql, parameterList, internalParameters, cursorFactory);
       this.rowType = rowType;
+      this.collationList = collationList;
       this.maxRowCount = maxRowCount;
       this.bindable = bindable;
     }
@@ -286,6 +286,10 @@ public interface CalcitePrepare {
       }
       return enumerable;
     }
+
+    public List<RelCollation> getCollationList() {
+      return collationList;
+    }
   }
 }
 

http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/87e7454c/core/src/main/java/org/apache/calcite/materialize/MaterializationService.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/materialize/MaterializationService.java b/core/src/main/java/org/apache/calcite/materialize/MaterializationService.java
index 615d185..fc9ac2b 100644
--- a/core/src/main/java/org/apache/calcite/materialize/MaterializationService.java
+++ b/core/src/main/java/org/apache/calcite/materialize/MaterializationService.java
@@ -369,6 +369,7 @@ public class MaterializationService {
           Schemas.prepare(connection, schema, viewSchemaPath, viewSql, map);
       return CloneSchema.createCloneTable(connection.getTypeFactory(),
           RelDataTypeImpl.proto(calciteSignature.rowType),
+          calciteSignature.getCollationList(),
           Lists.transform(calciteSignature.columns,
               new Function<ColumnMetaData, ColumnMetaData.Rep>() {
                 public ColumnMetaData.Rep apply(ColumnMetaData column) {

http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/87e7454c/core/src/main/java/org/apache/calcite/prepare/CalcitePrepareImpl.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/prepare/CalcitePrepareImpl.java b/core/src/main/java/org/apache/calcite/prepare/CalcitePrepareImpl.java
index b7f444f..524e34f 100644
--- a/core/src/main/java/org/apache/calcite/prepare/CalcitePrepareImpl.java
+++ b/core/src/main/java/org/apache/calcite/prepare/CalcitePrepareImpl.java
@@ -62,6 +62,7 @@ import org.apache.calcite.plan.RelOptUtil;
 import org.apache.calcite.plan.hep.HepPlanner;
 import org.apache.calcite.plan.hep.HepProgramBuilder;
 import org.apache.calcite.plan.volcano.VolcanoPlanner;
+import org.apache.calcite.rel.RelCollation;
 import org.apache.calcite.rel.RelCollationTraitDef;
 import org.apache.calcite.rel.RelNode;
 import org.apache.calcite.rel.core.Filter;
@@ -600,6 +601,7 @@ public class CalcitePrepareImpl implements CalcitePrepare {
         x,
         columns,
         cursorFactory,
+        ImmutableList.<RelCollation>of(),
         -1,
         new Bindable<T>() {
           public Enumerable<T> bind(DataContext dataContext) {
@@ -720,6 +722,9 @@ public class CalcitePrepareImpl implements CalcitePrepare {
         preparingStmt.resultConvention == BindableConvention.INSTANCE
             ? Meta.CursorFactory.ARRAY
             : Meta.CursorFactory.deduce(columns, resultClazz),
+        preparedResult instanceof Prepare.PreparedResultImpl
+            ? ((Prepare.PreparedResultImpl) preparedResult).collations
+            : ImmutableList.<RelCollation>of(),
         maxRowCount,
         bindable);
   }
@@ -1063,6 +1068,7 @@ public class CalcitePrepareImpl implements CalcitePrepare {
           resultType,
           parameterRowType,
           fieldOrigins,
+          ImmutableList.copyOf(collations),
           rootRel,
           mapTableModOp(isDml, sqlKind),
           isDml) {

http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/87e7454c/core/src/main/java/org/apache/calcite/prepare/Prepare.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/prepare/Prepare.java b/core/src/main/java/org/apache/calcite/prepare/Prepare.java
index 5892fa9..8ff5c0d 100644
--- a/core/src/main/java/org/apache/calcite/prepare/Prepare.java
+++ b/core/src/main/java/org/apache/calcite/prepare/Prepare.java
@@ -28,7 +28,9 @@ import org.apache.calcite.plan.RelOptSchema;
 import org.apache.calcite.plan.RelOptTable;
 import org.apache.calcite.plan.RelOptUtil;
 import org.apache.calcite.plan.RelTraitSet;
+import org.apache.calcite.rel.RelCollation;
 import org.apache.calcite.rel.RelNode;
+import org.apache.calcite.rel.core.Sort;
 import org.apache.calcite.rel.logical.LogicalTableModify;
 import org.apache.calcite.rel.type.RelDataType;
 import org.apache.calcite.rex.RexExecutorImpl;
@@ -55,6 +57,7 @@ import com.google.common.base.Preconditions;
 import com.google.common.collect.ImmutableList;
 
 import java.lang.reflect.Type;
+import java.util.ArrayList;
 import java.util.Collections;
 import java.util.List;
 import java.util.logging.Level;
@@ -76,6 +79,7 @@ public abstract class Prepare {
   protected final Convention resultConvention;
   protected CalciteTimingTracer timingTracer;
   protected List<List<String>> fieldOrigins;
+  protected final List<RelCollation> collations = new ArrayList<>();
   protected RelDataType parameterRowType;
 
   // temporary. for testing.
@@ -226,6 +230,11 @@ public abstract class Prepare {
       timingTracer.traceTime("end sql2rel");
     }
 
+    assert collations.isEmpty();
+    if (rootRel instanceof Sort) {
+      collations.add(((Sort) rootRel).getCollation());
+    }
+
     final RelDataType resultType = validator.getValidatedNodeType(sqlQuery);
     fieldOrigins = validator.getFieldOrigins(sqlQuery);
     assert fieldOrigins.size() == resultType.getFieldCount();
@@ -500,17 +509,20 @@ public abstract class Prepare {
     protected final boolean isDml;
     protected final LogicalTableModify.Operation tableModOp;
     protected final List<List<String>> fieldOrigins;
+    protected final List<RelCollation> collations;
 
     public PreparedResultImpl(
         RelDataType rowType,
         RelDataType parameterRowType,
         List<List<String>> fieldOrigins,
+        List<RelCollation> collations,
         RelNode rootRel,
         LogicalTableModify.Operation tableModOp,
         boolean isDml) {
       this.rowType = Preconditions.checkNotNull(rowType);
       this.parameterRowType = Preconditions.checkNotNull(parameterRowType);
       this.fieldOrigins = Preconditions.checkNotNull(fieldOrigins);
+      this.collations = ImmutableList.copyOf(collations);
       this.rootRel = Preconditions.checkNotNull(rootRel);
       this.tableModOp = tableModOp;
       this.isDml = isDml;

http://git-wip-us.apache.org/repos/asf/incubator-calcite/blob/87e7454c/core/src/main/java/org/apache/calcite/rel/RelCollations.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/calcite/rel/RelCollations.java b/core/src/main/java/org/apache/calcite/rel/RelCollations.java
index 2ee3b59..36f1327 100644
--- a/core/src/main/java/org/apache/calcite/rel/RelCollations.java
+++ b/core/src/main/java/org/apache/calcite/rel/RelCollations.java
@@ -63,14 +63,20 @@ public class RelCollations {
   }
 
   /**
+   * Creates a collation containing one field.
+   */
+  public static RelCollation of(int fieldIndex) {
+    return of(
+        new RelFieldCollation(fieldIndex,
+            RelFieldCollation.Direction.ASCENDING,
+            RelFieldCollation.NullDirection.UNSPECIFIED));
+  }
+
+  /**
    * Creates a list containing one collation containing one field.
    */
   public static List<RelCollation> createSingleton(int fieldIndex) {
-    return ImmutableList.of(
-        of(
-            new RelFieldCollation(fieldIndex,
-                RelFieldCollation.Direction.ASCENDING,
-                RelFieldCollation.NullDirection.UNSPECIFIED)));
+    return ImmutableList.of(of(fieldIndex));
   }
 
   /**