Merge pull request #26814 from ClickHouse/fix_lost_aggregate_function_parameters

Fix lost parameters of aggregate functions
This commit is contained in:
tavplubix 2021-07-29 13:43:05 +03:00 committed by GitHub
commit 4a3ade1aa5
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
16 changed files with 111 additions and 40 deletions

View File

@ -43,9 +43,9 @@ public:
const AggregateFunctionPtr & nested_function,
const AggregateFunctionProperties &,
const DataTypes & arguments,
const Array &) const override
const Array & params) const override
{
return std::make_shared<AggregateFunctionArray>(nested_function, arguments);
return std::make_shared<AggregateFunctionArray>(nested_function, arguments, params);
}
};

View File

@ -29,10 +29,11 @@ private:
size_t num_arguments;
public:
AggregateFunctionArray(AggregateFunctionPtr nested_, const DataTypes & arguments)
: IAggregateFunctionHelper<AggregateFunctionArray>(arguments, {})
AggregateFunctionArray(AggregateFunctionPtr nested_, const DataTypes & arguments, const Array & params_)
: IAggregateFunctionHelper<AggregateFunctionArray>(arguments, params_)
, nested_func(nested_), num_arguments(arguments.size())
{
assert(parameters == nested_func->getParameters());
for (const auto & type : arguments)
if (!isArray(type))
throw Exception("All arguments for aggregate function " + getName() + " must be arrays", ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT);

View File

@ -34,14 +34,14 @@ public:
const AggregateFunctionPtr & nested_function,
const AggregateFunctionProperties &,
const DataTypes & arguments,
const Array &) const override
const Array & params) const override
{
AggregateFunctionPtr res;
if (arguments.size() == 1)
{
res.reset(createWithNumericType<
AggregateFunctionDistinct,
AggregateFunctionDistinctSingleNumericData>(*arguments[0], nested_function, arguments));
AggregateFunctionDistinctSingleNumericData>(*arguments[0], nested_function, arguments, params));
if (res)
return res;
@ -49,14 +49,14 @@ public:
if (arguments[0]->isValueUnambiguouslyRepresentedInContiguousMemoryRegion())
return std::make_shared<
AggregateFunctionDistinct<
AggregateFunctionDistinctSingleGenericData<true>>>(nested_function, arguments);
AggregateFunctionDistinctSingleGenericData<true>>>(nested_function, arguments, params);
else
return std::make_shared<
AggregateFunctionDistinct<
AggregateFunctionDistinctSingleGenericData<false>>>(nested_function, arguments);
AggregateFunctionDistinctSingleGenericData<false>>>(nested_function, arguments, params);
}
return std::make_shared<AggregateFunctionDistinct<AggregateFunctionDistinctMultipleGenericData>>(nested_function, arguments);
return std::make_shared<AggregateFunctionDistinct<AggregateFunctionDistinctMultipleGenericData>>(nested_function, arguments, params);
}
};

View File

@ -167,8 +167,8 @@ private:
}
public:
AggregateFunctionDistinct(AggregateFunctionPtr nested_func_, const DataTypes & arguments)
: IAggregateFunctionDataHelper<Data, AggregateFunctionDistinct>(arguments, nested_func_->getParameters())
AggregateFunctionDistinct(AggregateFunctionPtr nested_func_, const DataTypes & arguments, const Array & params_)
: IAggregateFunctionDataHelper<Data, AggregateFunctionDistinct>(arguments, params_)
, nested_func(nested_func_)
, arguments_num(arguments.size()) {}

View File

@ -38,9 +38,9 @@ public:
const AggregateFunctionPtr & nested_function,
const AggregateFunctionProperties &,
const DataTypes & arguments,
const Array &) const override
const Array & params) const override
{
return std::make_shared<AggregateFunctionForEach>(nested_function, arguments);
return std::make_shared<AggregateFunctionForEach>(nested_function, arguments, params);
}
};

View File

@ -105,8 +105,8 @@ private:
}
public:
AggregateFunctionForEach(AggregateFunctionPtr nested_, const DataTypes & arguments)
: IAggregateFunctionDataHelper<AggregateFunctionForEachData, AggregateFunctionForEach>(arguments, {})
AggregateFunctionForEach(AggregateFunctionPtr nested_, const DataTypes & arguments, const Array & params_)
: IAggregateFunctionDataHelper<AggregateFunctionForEachData, AggregateFunctionForEach>(arguments, params_)
, nested_func(nested_), num_arguments(arguments.size())
{
nested_size_of_data = nested_func->sizeOfData();

View File

@ -25,8 +25,8 @@ template <typename HasLimit>
class AggregateFunctionGroupUniqArrayDate : public AggregateFunctionGroupUniqArray<DataTypeDate::FieldType, HasLimit>
{
public:
explicit AggregateFunctionGroupUniqArrayDate(const DataTypePtr & argument_type, UInt64 max_elems_ = std::numeric_limits<UInt64>::max())
: AggregateFunctionGroupUniqArray<DataTypeDate::FieldType, HasLimit>(argument_type, max_elems_) {}
explicit AggregateFunctionGroupUniqArrayDate(const DataTypePtr & argument_type, const Array & parameters_, UInt64 max_elems_ = std::numeric_limits<UInt64>::max())
: AggregateFunctionGroupUniqArray<DataTypeDate::FieldType, HasLimit>(argument_type, parameters_, max_elems_) {}
DataTypePtr getReturnType() const override { return std::make_shared<DataTypeArray>(std::make_shared<DataTypeDate>()); }
};
@ -34,8 +34,8 @@ template <typename HasLimit>
class AggregateFunctionGroupUniqArrayDateTime : public AggregateFunctionGroupUniqArray<DataTypeDateTime::FieldType, HasLimit>
{
public:
explicit AggregateFunctionGroupUniqArrayDateTime(const DataTypePtr & argument_type, UInt64 max_elems_ = std::numeric_limits<UInt64>::max())
: AggregateFunctionGroupUniqArray<DataTypeDateTime::FieldType, HasLimit>(argument_type, max_elems_) {}
explicit AggregateFunctionGroupUniqArrayDateTime(const DataTypePtr & argument_type, const Array & parameters_, UInt64 max_elems_ = std::numeric_limits<UInt64>::max())
: AggregateFunctionGroupUniqArray<DataTypeDateTime::FieldType, HasLimit>(argument_type, parameters_, max_elems_) {}
DataTypePtr getReturnType() const override { return std::make_shared<DataTypeArray>(std::make_shared<DataTypeDateTime>()); }
};
@ -102,9 +102,9 @@ AggregateFunctionPtr createAggregateFunctionGroupUniqArray(
ErrorCodes::NUMBER_OF_ARGUMENTS_DOESNT_MATCH);
if (!limit_size)
return createAggregateFunctionGroupUniqArrayImpl<std::false_type>(name, argument_types[0]);
return createAggregateFunctionGroupUniqArrayImpl<std::false_type>(name, argument_types[0], parameters);
else
return createAggregateFunctionGroupUniqArrayImpl<std::true_type>(name, argument_types[0], max_elems);
return createAggregateFunctionGroupUniqArrayImpl<std::true_type>(name, argument_types[0], parameters, max_elems);
}
}

View File

@ -48,9 +48,9 @@ private:
using State = AggregateFunctionGroupUniqArrayData<T>;
public:
AggregateFunctionGroupUniqArray(const DataTypePtr & argument_type, UInt64 max_elems_ = std::numeric_limits<UInt64>::max())
AggregateFunctionGroupUniqArray(const DataTypePtr & argument_type, const Array & parameters_, UInt64 max_elems_ = std::numeric_limits<UInt64>::max())
: IAggregateFunctionDataHelper<AggregateFunctionGroupUniqArrayData<T>,
AggregateFunctionGroupUniqArray<T, Tlimit_num_elem>>({argument_type}, {}),
AggregateFunctionGroupUniqArray<T, Tlimit_num_elem>>({argument_type}, parameters_),
max_elems(max_elems_) {}
String getName() const override { return "groupUniqArray"; }
@ -152,8 +152,8 @@ class AggregateFunctionGroupUniqArrayGeneric
using State = AggregateFunctionGroupUniqArrayGenericData;
public:
AggregateFunctionGroupUniqArrayGeneric(const DataTypePtr & input_data_type_, UInt64 max_elems_ = std::numeric_limits<UInt64>::max())
: IAggregateFunctionDataHelper<AggregateFunctionGroupUniqArrayGenericData, AggregateFunctionGroupUniqArrayGeneric<is_plain_column, Tlimit_num_elem>>({input_data_type_}, {})
AggregateFunctionGroupUniqArrayGeneric(const DataTypePtr & input_data_type_, const Array & parameters_, UInt64 max_elems_ = std::numeric_limits<UInt64>::max())
: IAggregateFunctionDataHelper<AggregateFunctionGroupUniqArrayGenericData, AggregateFunctionGroupUniqArrayGeneric<is_plain_column, Tlimit_num_elem>>({input_data_type_}, parameters_)
, input_data_type(this->argument_types[0])
, max_elems(max_elems_) {}

View File

@ -35,9 +35,9 @@ public:
const AggregateFunctionPtr & nested_function,
const AggregateFunctionProperties &,
const DataTypes & arguments,
const Array &) const override
const Array & params) const override
{
return std::make_shared<AggregateFunctionIf>(nested_function, arguments);
return std::make_shared<AggregateFunctionIf>(nested_function, arguments, params);
}
};

View File

@ -37,8 +37,8 @@ private:
size_t num_arguments;
public:
AggregateFunctionIf(AggregateFunctionPtr nested, const DataTypes & types)
: IAggregateFunctionHelper<AggregateFunctionIf>(types, nested->getParameters())
AggregateFunctionIf(AggregateFunctionPtr nested, const DataTypes & types, const Array & params_)
: IAggregateFunctionHelper<AggregateFunctionIf>(types, params_)
, nested_func(nested), num_arguments(types.size())
{
if (num_arguments == 0)

View File

@ -39,7 +39,7 @@ public:
const AggregateFunctionPtr & nested_function,
const AggregateFunctionProperties &,
const DataTypes & arguments,
const Array &) const override
const Array & params) const override
{
const DataTypePtr & argument = arguments[0];
@ -53,7 +53,7 @@ public:
+ ", because it corresponds to different aggregate function: " + function->getFunctionName() + " instead of " + nested_function->getName(),
ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT);
return std::make_shared<AggregateFunctionMerge>(nested_function, argument);
return std::make_shared<AggregateFunctionMerge>(nested_function, argument, params);
}
};

View File

@ -29,8 +29,8 @@ private:
AggregateFunctionPtr nested_func;
public:
AggregateFunctionMerge(const AggregateFunctionPtr & nested_, const DataTypePtr & argument)
: IAggregateFunctionHelper<AggregateFunctionMerge>({argument}, nested_->getParameters())
AggregateFunctionMerge(const AggregateFunctionPtr & nested_, const DataTypePtr & argument, const Array & params_)
: IAggregateFunctionHelper<AggregateFunctionMerge>({argument}, params_)
, nested_func(nested_)
{
const DataTypeAggregateFunction * data_type = typeid_cast<const DataTypeAggregateFunction *>(argument.get());

View File

@ -1,3 +1,6 @@
5 5
5 5
5 5
5 5
5 5
5 5

View File

@ -4,16 +4,20 @@ CURDIR=$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)
# shellcheck source=../shell_config.sh
. "$CURDIR"/../shell_config.sh
declare -a functions=("groupArraySample" "groupUniqArray")
declare -a engines=("Memory" "MergeTree order by n" "Log")
for engine in "${engines[@]}"
for func in "${functions[@]}"
do
$CLICKHOUSE_CLIENT -q "drop table if exists t";
$CLICKHOUSE_CLIENT -q "create table t (n UInt8, a1 AggregateFunction(groupArraySample(1), UInt8)) engine=$engine"
$CLICKHOUSE_CLIENT -q "insert into t select number % 5 as n, groupArraySampleState(1)(toUInt8(number)) from numbers(10) group by n"
for engine in "${engines[@]}"
do
$CLICKHOUSE_CLIENT -q "drop table if exists t";
$CLICKHOUSE_CLIENT -q "create table t (n UInt8, a1 AggregateFunction($func(1), UInt8)) engine=$engine"
$CLICKHOUSE_CLIENT -q "insert into t select number % 5 as n, ${func}State(1)(toUInt8(number)) from numbers(10) group by n"
$CLICKHOUSE_CLIENT -q "select * from t format TSV" | $CLICKHOUSE_CLIENT -q "insert into t format TSV"
$CLICKHOUSE_CLIENT -q "select countDistinct(n), countDistinct(a1) from t"
$CLICKHOUSE_CLIENT -q "select * from t format TSV" | $CLICKHOUSE_CLIENT -q "insert into t format TSV"
$CLICKHOUSE_CLIENT -q "select countDistinct(n), countDistinct(a1) from t"
$CLICKHOUSE_CLIENT -q "drop table t";
$CLICKHOUSE_CLIENT -q "drop table t";
done
done

View File

@ -0,0 +1,20 @@
AggregateFunction(topKArray(10), Array(String))
AggregateFunction(topKDistinct(10), String)
AggregateFunction(topKForEach(10), Array(String))
AggregateFunction(topKIf(10), String, UInt8)
AggregateFunction(topK(10), String)
AggregateFunction(topKOrNull(10), String)
AggregateFunction(topKOrDefault(10), String)
AggregateFunction(topKResample(10, 1, 2, 42), String, UInt64)
AggregateFunction(topK(10), String)
AggregateFunction(topKArrayResampleOrDefaultIf(10, 1, 2, 42), Array(String), UInt64, UInt8)
10
10
[10]
11
10
10
10
[1]
10
[1]

View File

@ -0,0 +1,43 @@
SELECT toTypeName(topKArrayState(10)([toString(number)])) FROM numbers(100);
SELECT toTypeName(topKDistinctState(10)(toString(number))) FROM numbers(100);
SELECT toTypeName(topKForEachState(10)([toString(number)])) FROM numbers(100);
SELECT toTypeName(topKIfState(10)(toString(number), number % 2)) FROM numbers(100);
SELECT toTypeName(topKMergeState(10)(state)) FROM (SELECT topKState(10)(toString(number)) as state FROM numbers(100));
SELECT toTypeName(topKOrNullState(10)(toString(number))) FROM numbers(100);
SELECT toTypeName(topKOrDefaultState(10)(toString(number))) FROM numbers(100);
SELECT toTypeName(topKResampleState(10, 1, 2, 42)(toString(number), number)) FROM numbers(100);
SELECT toTypeName(topKState(10)(toString(number))) FROM numbers(100);
SELECT toTypeName(topKArrayResampleOrDefaultIfState(10, 1, 2, 42)([toString(number)], number, number % 2)) FROM numbers(100);
CREATE TEMPORARY TABLE t0 AS SELECT quantileArrayState(0.10)([number]) FROM numbers(100);
CREATE TEMPORARY TABLE t1 AS SELECT quantileDistinctState(0.10)(number) FROM numbers(100);
CREATE TEMPORARY TABLE t2 AS SELECT quantileForEachState(0.10)([number]) FROM numbers(100);
CREATE TEMPORARY TABLE t3 AS SELECT quantileIfState(0.10)(number, number % 2) FROM numbers(100);
CREATE TEMPORARY TABLE t4 AS SELECT quantileMergeState(0.10)(state) FROM (SELECT quantileState(0.10)(number) as state FROM numbers(100));
CREATE TEMPORARY TABLE t5 AS SELECT quantileOrNullState(0.10)(number) FROM numbers(100);
CREATE TEMPORARY TABLE t6 AS SELECT quantileOrDefaultState(0.10)(number) FROM numbers(100);
CREATE TEMPORARY TABLE t7 AS SELECT quantileResampleState(0.10, 1, 2, 42)(number, number) FROM numbers(100);
CREATE TEMPORARY TABLE t8 AS SELECT quantileState(0.10)(number) FROM numbers(100);
CREATE TEMPORARY TABLE t9 AS SELECT quantileArrayResampleOrDefaultIfState(0.10, 1, 2, 42)([number], number, number % 2) FROM numbers(100);
INSERT INTO t0 SELECT quantileArrayState(0.10)([number]) FROM numbers(100);
INSERT INTO t1 SELECT quantileDistinctState(0.10)(number) FROM numbers(100);
INSERT INTO t2 SELECT quantileForEachState(0.10)([number]) FROM numbers(100);
INSERT INTO t3 SELECT quantileIfState(0.10)(number, number % 2) FROM numbers(100);
INSERT INTO t4 SELECT quantileMergeState(0.10)(state) FROM (SELECT quantileState(0.10)(number) as state FROM numbers(100));
INSERT INTO t5 SELECT quantileOrNullState(0.10)(number) FROM numbers(100);
INSERT INTO t6 SELECT quantileOrDefaultState(0.10)(number) FROM numbers(100);
INSERT INTO t7 SELECT quantileResampleState(0.10, 1, 2, 42)(number, number) FROM numbers(100);
INSERT INTO t8 SELECT quantileState(0.10)(number) FROM numbers(100);
INSERT INTO t9 SELECT quantileArrayResampleOrDefaultIfState(0.10, 1, 2, 42)([number], number, number % 2) FROM numbers(100);
SELECT round(quantileArrayMerge(0.10)((*,).1)) FROM t0;
SELECT round(quantileDistinctMerge(0.10)((*,).1)) FROM t1;
SELECT arrayMap(x -> round(x), quantileForEachMerge(0.10)((*,).1)) FROM t2;
SELECT round(quantileIfMerge(0.10)((*,).1)) FROM t3;
SELECT round(quantileMerge(0.10)((*,).1)) FROM t4;
SELECT round(quantileOrNullMerge(0.10)((*,).1)) FROM t5;
SELECT round(quantileOrDefaultMerge(0.10)((*,).1)) FROM t6;
SELECT arrayMap(x -> round(x), quantileResampleMerge(0.10, 1, 2, 42)((*,).1)) FROM t7;
SELECT round(quantileMerge(0.10)((*,).1)) FROM t8;
SELECT arrayMap(x -> round(x), quantileArrayResampleOrDefaultIfMerge(0.10, 1, 2, 42)((*,).1)) FROM t9;