This is an automated email from the ASF dual-hosted git repository.

jiajunxie pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/calcite.git


The following commit(s) were added to refs/heads/main by this push:
     new 48f51ea5d9 [CALCITE-5700] Add ARRAY_SIZE, ARRAY_REPEAT function 
(enabled in Spark library).
48f51ea5d9 is described below

commit 48f51ea5d9443fb11e070eea094bf551c8ff22fc
Author: yongen.ly <yongen...@alibaba-inc.com>
AuthorDate: Fri May 12 15:06:00 2023 +0800

    [CALCITE-5700] Add ARRAY_SIZE, ARRAY_REPEAT function (enabled in Spark 
library).
---
 .../calcite/adapter/enumerable/RexImpTable.java    |  4 +++
 .../org/apache/calcite/runtime/SqlFunctions.java   | 12 ++++++++
 .../main/java/org/apache/calcite/sql/SqlKind.java  |  6 ++++
 .../calcite/sql/fun/SqlLibraryOperators.java       | 16 ++++++++++
 .../org/apache/calcite/util/BuiltInMethod.java     |  1 +
 site/_docs/reference.md                            |  2 ++
 .../org/apache/calcite/test/SqlOperatorTest.java   | 36 ++++++++++++++++++++++
 7 files changed, 77 insertions(+)

diff --git 
a/core/src/main/java/org/apache/calcite/adapter/enumerable/RexImpTable.java 
b/core/src/main/java/org/apache/calcite/adapter/enumerable/RexImpTable.java
index bf835c0d18..16a9df8632 100644
--- a/core/src/main/java/org/apache/calcite/adapter/enumerable/RexImpTable.java
+++ b/core/src/main/java/org/apache/calcite/adapter/enumerable/RexImpTable.java
@@ -118,7 +118,9 @@ import static 
org.apache.calcite.sql.fun.SqlLibraryOperators.ARRAY_CONCAT;
 import static org.apache.calcite.sql.fun.SqlLibraryOperators.ARRAY_CONCAT_AGG;
 import static org.apache.calcite.sql.fun.SqlLibraryOperators.ARRAY_DISTINCT;
 import static org.apache.calcite.sql.fun.SqlLibraryOperators.ARRAY_LENGTH;
+import static org.apache.calcite.sql.fun.SqlLibraryOperators.ARRAY_REPEAT;
 import static org.apache.calcite.sql.fun.SqlLibraryOperators.ARRAY_REVERSE;
+import static org.apache.calcite.sql.fun.SqlLibraryOperators.ARRAY_SIZE;
 import static org.apache.calcite.sql.fun.SqlLibraryOperators.BOOL_AND;
 import static org.apache.calcite.sql.fun.SqlLibraryOperators.BOOL_OR;
 import static org.apache.calcite.sql.fun.SqlLibraryOperators.CHAR;
@@ -671,7 +673,9 @@ public class RexImpTable {
       defineMethod(STRUCT_ACCESS, BuiltInMethod.STRUCT_ACCESS.method, 
NullPolicy.ANY);
       defineMethod(MEMBER_OF, BuiltInMethod.MEMBER_OF.method, NullPolicy.NONE);
       defineMethod(ARRAY_DISTINCT, BuiltInMethod.ARRAY_DISTINCT.method, 
NullPolicy.STRICT);
+      defineMethod(ARRAY_REPEAT, BuiltInMethod.ARRAY_REPEAT.method, 
NullPolicy.NONE);
       defineMethod(ARRAY_REVERSE, BuiltInMethod.ARRAY_REVERSE.method, 
NullPolicy.STRICT);
+      defineMethod(ARRAY_SIZE, BuiltInMethod.COLLECTION_SIZE.method, 
NullPolicy.STRICT);
       map.put(ARRAY_CONCAT, new ArrayConcatImplementor());
       final MethodImplementor isEmptyImplementor =
           new MethodImplementor(BuiltInMethod.IS_EMPTY.method, NullPolicy.NONE,
diff --git a/core/src/main/java/org/apache/calcite/runtime/SqlFunctions.java 
b/core/src/main/java/org/apache/calcite/runtime/SqlFunctions.java
index 75ced53c9a..52c2da6878 100644
--- a/core/src/main/java/org/apache/calcite/runtime/SqlFunctions.java
+++ b/core/src/main/java/org/apache/calcite/runtime/SqlFunctions.java
@@ -3797,6 +3797,18 @@ public class SqlFunctions {
     return new ArrayList<>(result);
   }
 
+  /** Support the ARRAY_REPEAT function. */
+  public static @Nullable List<Object> repeat(Object element, Object count) {
+    if (count == null) {
+      return null;
+    }
+    int numberOfElement = (int) count;
+    if (numberOfElement < 0) {
+      numberOfElement = 0;
+    }
+    return Collections.nCopies(numberOfElement, element);
+  }
+
   /** Support the SLICE function. */
   public static List slice(List list) {
     List result = new ArrayList(list.size());
diff --git a/core/src/main/java/org/apache/calcite/sql/SqlKind.java 
b/core/src/main/java/org/apache/calcite/sql/SqlKind.java
index 44cd4cd02d..9104af350c 100644
--- a/core/src/main/java/org/apache/calcite/sql/SqlKind.java
+++ b/core/src/main/java/org/apache/calcite/sql/SqlKind.java
@@ -683,9 +683,15 @@ public enum SqlKind {
   /** {@code ARRAY_DISTINCT} function (Spark semantics). */
   ARRAY_DISTINCT,
 
+  /** {@code ARRAY_REPEAT} function (Spark semantics). */
+  ARRAY_REPEAT,
+
   /** {@code ARRAY_REVERSE} function (BigQuery semantics). */
   ARRAY_REVERSE,
 
+  /** {@code ARRAY_SIZE} function (Spark semantics). */
+  ARRAY_SIZE,
+
   /** {@code REVERSE} function (SQL Server, MySQL). */
   REVERSE,
 
diff --git 
a/core/src/main/java/org/apache/calcite/sql/fun/SqlLibraryOperators.java 
b/core/src/main/java/org/apache/calcite/sql/fun/SqlLibraryOperators.java
index 7eedae2918..4ae48490e5 100644
--- a/core/src/main/java/org/apache/calcite/sql/fun/SqlLibraryOperators.java
+++ b/core/src/main/java/org/apache/calcite/sql/fun/SqlLibraryOperators.java
@@ -858,6 +858,15 @@ public abstract class SqlLibraryOperators {
           ReturnTypes.INTEGER_NULLABLE,
           OperandTypes.ARRAY);
 
+  /** The "ARRAY_REPEAT(element, count)" function. */
+  @LibraryOperator(libraries = {SPARK})
+  public static final SqlFunction ARRAY_REPEAT =
+      SqlBasicFunction.create(SqlKind.ARRAY_REPEAT,
+          ReturnTypes.TO_ARRAY,
+          OperandTypes.sequence(
+              "ARRAY_REPEAT(ANY, INTEGER)",
+              OperandTypes.ANY, OperandTypes.typeName(SqlTypeName.INTEGER)));
+
   /** The "ARRAY_REVERSE(array)" function. */
   @LibraryOperator(libraries = {BIG_QUERY})
   public static final SqlFunction ARRAY_REVERSE =
@@ -865,6 +874,13 @@ public abstract class SqlLibraryOperators {
           ReturnTypes.ARG0_NULLABLE,
           OperandTypes.ARRAY);
 
+  /** The "ARRAY_SIZE(array)" function. */
+  @LibraryOperator(libraries = {SPARK})
+  public static final SqlFunction ARRAY_SIZE =
+      SqlBasicFunction.create(SqlKind.ARRAY_SIZE,
+          ReturnTypes.INTEGER_NULLABLE,
+          OperandTypes.ARRAY);
+
   /** The "ARRAY_CONCAT(array [, array]*)" function. */
   @LibraryOperator(libraries = {BIG_QUERY})
   public static final SqlFunction ARRAY_CONCAT =
diff --git a/core/src/main/java/org/apache/calcite/util/BuiltInMethod.java 
b/core/src/main/java/org/apache/calcite/util/BuiltInMethod.java
index 90eb4df0fc..13bc6ec051 100644
--- a/core/src/main/java/org/apache/calcite/util/BuiltInMethod.java
+++ b/core/src/main/java/org/apache/calcite/util/BuiltInMethod.java
@@ -629,6 +629,7 @@ public enum BuiltInMethod {
   SUBMULTISET_OF(SqlFunctions.class, "submultisetOf", Collection.class,
       Collection.class),
   ARRAY_DISTINCT(SqlFunctions.class, "distinct", List.class),
+  ARRAY_REPEAT(SqlFunctions.class, "repeat", Object.class, Integer.class),
   ARRAY_REVERSE(SqlFunctions.class, "reverse", List.class),
   SELECTIVITY(Selectivity.class, "getSelectivity", RexNode.class),
   UNIQUE_KEYS(UniqueKeys.class, "getUniqueKeys", boolean.class),
diff --git a/site/_docs/reference.md b/site/_docs/reference.md
index 30631bee36..47262a2d71 100644
--- a/site/_docs/reference.md
+++ b/site/_docs/reference.md
@@ -2654,7 +2654,9 @@ BigQuery's type system uses confusingly different names 
for types and functions:
 | b | ARRAY_CONCAT(array [, array ]*)                | Concatenates one or 
more arrays. If any input argument is `NULL` the function returns `NULL`
 | s | ARRAY_DISTINCT(array)                          | Returns unique elements 
of *array*. Keeps ordering of elements.
 | b | ARRAY_LENGTH(array)                            | Synonym for 
`CARDINALITY`
+| s | ARRAY_REPEAT(element, count)                   | Returns the array 
containing element count times.
 | b | ARRAY_REVERSE(array)                           | Reverses elements of 
*array*
+| s | ARRAY_SIZE(array)                              | Synonym for 
`CARDINALITY`
 | m s | CHAR(integer)                                | Returns the character 
whose ASCII code is *integer* % 256, or null if *integer* &lt; 0
 | b o p | CHR(integer)                               | Returns the character 
whose UTF-8 code is *integer*
 | o | CONCAT(string, string)                         | Concatenates two strings
diff --git a/testkit/src/main/java/org/apache/calcite/test/SqlOperatorTest.java 
b/testkit/src/main/java/org/apache/calcite/test/SqlOperatorTest.java
index 338ac1bebe..fe4a8cac0c 100644
--- a/testkit/src/main/java/org/apache/calcite/test/SqlOperatorTest.java
+++ b/testkit/src/main/java/org/apache/calcite/test/SqlOperatorTest.java
@@ -5336,6 +5336,27 @@ public class SqlOperatorTest {
     f.checkNull("array_distinct(null)");
   }
 
+  /** Tests {@code ARRAY_REPEAT} function from Spark. */
+  @Test void testArrayRepeatFunc() {
+    final SqlOperatorFixture f0 = fixture();
+    f0.setFor(SqlLibraryOperators.ARRAY_REPEAT);
+    f0.checkFails("^array_repeat(1, 2)^",
+        "No match found for function signature ARRAY_REPEAT\\(<NUMERIC>, 
<NUMERIC>\\)", false);
+
+    final SqlOperatorFixture f = f0.withLibrary(SqlLibrary.SPARK);
+    f.checkScalar("array_repeat(1, 2)", "[1, 1]",
+        "INTEGER NOT NULL ARRAY NOT NULL");
+    f.checkScalar("array_repeat(1, -2)", "[]",
+        "INTEGER NOT NULL ARRAY NOT NULL");
+    f.checkScalar("array_repeat(array[1, 2], 2)", "[[1, 2], [1, 2]]",
+        "INTEGER NOT NULL ARRAY NOT NULL ARRAY NOT NULL");
+    f.checkScalar("array_repeat(map[1, 'a', 2, 'b'], 2)", "[{1=a, 2=b}, {1=a, 
2=b}]",
+        "(INTEGER NOT NULL, CHAR(1) NOT NULL) MAP NOT NULL ARRAY NOT NULL");
+    f.checkScalar("array_repeat(cast(null as integer), 2)", "[null, null]",
+        "INTEGER ARRAY NOT NULL");
+    f.checkNull("array_repeat(1, null)");
+  }
+
   /** Tests {@code ARRAY_REVERSE} function from BigQuery. */
   @Test void testArrayReverseFunc() {
     SqlOperatorFixture f = fixture()
@@ -5349,6 +5370,21 @@ public class SqlOperatorTest {
         "INTEGER ARRAY NOT NULL");
   }
 
+  /** Tests {@code ARRAY_SIZE} function from Spark. */
+  @Test void testArraySizeFunc() {
+    final SqlOperatorFixture f0 = fixture();
+    f0.setFor(SqlLibraryOperators.ARRAY_SIZE);
+    f0.checkFails("^array_size(array[1])^",
+        "No match found for function signature ARRAY_SIZE\\(<INTEGER 
ARRAY>\\)", false);
+
+    final SqlOperatorFixture f = f0.withLibrary(SqlLibrary.SPARK);
+    f.checkScalar("array_size(array[1])", "1",
+        "INTEGER NOT NULL");
+    f.checkScalar("array_size(array[1, 2, null])", "3",
+        "INTEGER NOT NULL");
+    f.checkNull("array_size(null)");
+  }
+
   /** Tests {@code ARRAY_LENGTH} function from BigQuery. */
   @Test void testArrayLengthFunc() {
     SqlOperatorFixture f = fixture()

Reply via email to