[Improve](complex-type) Support Count(complexType) (#17868)
Support count function for ARRAY/MAP/STRUCT type
This commit is contained in:
@ -699,7 +699,7 @@ public class FunctionCallExpr extends Expr {
|
||||
}
|
||||
|
||||
for (Expr child : children) {
|
||||
if (child.type.isOnlyMetricType()) {
|
||||
if (child.type.isOnlyMetricType() && !child.type.isComplexType()) {
|
||||
throw new AnalysisException(Type.OnlyMetricTypeErrorMsg);
|
||||
}
|
||||
}
|
||||
|
||||
@ -24,8 +24,6 @@ import org.apache.doris.catalog.Function;
|
||||
import org.apache.doris.catalog.Function.NullableMode;
|
||||
import org.apache.doris.catalog.FunctionSet;
|
||||
import org.apache.doris.catalog.ScalarFunction;
|
||||
import org.apache.doris.catalog.StructField;
|
||||
import org.apache.doris.catalog.StructType;
|
||||
import org.apache.doris.catalog.Type;
|
||||
import org.apache.doris.common.AnalysisException;
|
||||
import org.apache.doris.thrift.TExprNode;
|
||||
@ -62,7 +60,7 @@ public class IsNullPredicate extends Predicate {
|
||||
isNotNullSymbol, Lists.newArrayList(t), Type.BOOLEAN, NullableMode.ALWAYS_NOT_NULLABLE));
|
||||
|
||||
// for array type
|
||||
for (Type complexType : Lists.newArrayList(Type.ARRAY, Type.MAP)) {
|
||||
for (Type complexType : Lists.newArrayList(Type.ARRAY, Type.MAP, Type.GENERIC_STRUCT)) {
|
||||
functionSet.addBuiltinBothScalaAndVectorized(ScalarFunction.createBuiltinOperator(IS_NULL, isNullSymbol,
|
||||
Lists.newArrayList(complexType), Type.BOOLEAN, NullableMode.ALWAYS_NOT_NULLABLE));
|
||||
|
||||
@ -71,12 +69,6 @@ public class IsNullPredicate extends Predicate {
|
||||
NullableMode.ALWAYS_NOT_NULLABLE));
|
||||
}
|
||||
|
||||
Type nullStruct = new StructType(Lists.newArrayList(new StructField("null_pred", Type.NULL)));
|
||||
functionSet.addBuiltinBothScalaAndVectorized(ScalarFunction.createBuiltinOperator(IS_NULL, isNullSymbol,
|
||||
Lists.newArrayList(nullStruct), Type.BOOLEAN, NullableMode.ALWAYS_NOT_NULLABLE));
|
||||
|
||||
functionSet.addBuiltinBothScalaAndVectorized(ScalarFunction.createBuiltinOperator(IS_NOT_NULL,
|
||||
isNotNullSymbol, Lists.newArrayList(nullStruct), Type.BOOLEAN, NullableMode.ALWAYS_NOT_NULLABLE));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -1564,6 +1564,27 @@ public class FunctionSet<T> {
|
||||
prefix + "17count_star_removeEPN9doris_udf15FunctionContextEPNS1_9BigIntValE",
|
||||
null, false, true, true, true));
|
||||
|
||||
// count(array/map/struct)
|
||||
for (Type complexType : Lists.newArrayList(Type.ARRAY, Type.MAP, Type.GENERIC_STRUCT)) {
|
||||
addBuiltin(AggregateFunction.createBuiltin(FunctionSet.COUNT,
|
||||
Lists.newArrayList(complexType), Type.BIGINT, Type.BIGINT,
|
||||
prefix + "18init_zero_not_nullIN9doris_udf9BigIntValEEEvPNS2_15FunctionContextEPT_",
|
||||
prefix + "12count_updateEPN9doris_udf15FunctionContextERKNS1_6AnyValEPNS1_9BigIntValE",
|
||||
prefix + "11count_mergeEPN9doris_udf15FunctionContextERKNS1_9BigIntValEPS4_",
|
||||
null, null,
|
||||
prefix + "12count_removeEPN9doris_udf15FunctionContextERKNS1_6AnyValEPNS1_9BigIntValE",
|
||||
null, false, true, true, true));
|
||||
|
||||
addBuiltin(AggregateFunction.createBuiltin(FunctionSet.COUNT,
|
||||
Lists.newArrayList(complexType), Type.BIGINT, Type.BIGINT,
|
||||
prefix + "18init_zero_not_nullIN9doris_udf9BigIntValEEEvPNS2_15FunctionContextEPT_",
|
||||
prefix + "12count_updateEPN9doris_udf15FunctionContextERKNS1_6AnyValEPNS1_9BigIntValE",
|
||||
prefix + "11count_mergeEPN9doris_udf15FunctionContextERKNS1_9BigIntValEPS4_",
|
||||
null, null,
|
||||
prefix + "12count_removeEPN9doris_udf15FunctionContextERKNS1_6AnyValEPNS1_9BigIntValE",
|
||||
null, false, true, true, true));
|
||||
}
|
||||
|
||||
// windowFunnel
|
||||
addBuiltin(AggregateFunction.createBuiltin(FunctionSet.WINDOW_FUNNEL,
|
||||
Lists.newArrayList(Type.BIGINT, Type.STRING, Type.DATETIME, Type.BOOLEAN),
|
||||
|
||||
@ -20,6 +20,7 @@ package org.apache.doris.analysis;
|
||||
import org.apache.doris.common.Config;
|
||||
import org.apache.doris.utframe.TestWithFeService;
|
||||
|
||||
import org.junit.jupiter.api.Assertions;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
public class IsNullPredicateWithComplexTypeTest extends TestWithFeService {
|
||||
@ -53,8 +54,19 @@ public class IsNullPredicateWithComplexTypeTest extends TestWithFeService {
|
||||
String testStructIsNUll = "select * from test.complex where s is null";
|
||||
String testMapIsNUll = "select * from test.complex where m is null";
|
||||
String testArrayIsNUll = "select * from test.complex where a is null";
|
||||
assertSQLPlanOrErrorMsgContains(testStructIsNUll, "");
|
||||
assertSQLPlanOrErrorMsgContains(testMapIsNUll, "");
|
||||
assertSQLPlanOrErrorMsgContains(testArrayIsNUll, "");
|
||||
Assertions.assertNotNull(getSQLPlanner(testStructIsNUll));
|
||||
Assertions.assertNotNull(getSQLPlanner(testMapIsNUll));
|
||||
Assertions.assertNotNull(getSQLPlanner(testArrayIsNUll));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCount() throws Exception {
|
||||
String testStructIsNUll = "select count(s) from test.complex";
|
||||
String testMapIsNUll = "select count(m) from test.complex";
|
||||
String testArrayIsNUll = "select count(a) from test.complex";
|
||||
Assertions.assertNotNull(getSQLPlanner(testStructIsNUll));
|
||||
Assertions.assertNotNull(getSQLPlanner(testMapIsNUll));
|
||||
Assertions.assertNotNull(getSQLPlanner(testArrayIsNUll));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user