mirror of
https://github.com/ClickHouse/ClickHouse.git
synced 2024-11-26 17:41:59 +00:00
Merge remote-tracking branch 'upstream/master'
This commit is contained in:
commit
68309b75a8
@ -18,6 +18,9 @@ public:
|
|||||||
|
|
||||||
DataTypes transformArguments(const DataTypes & arguments) const override
|
DataTypes transformArguments(const DataTypes & arguments) const override
|
||||||
{
|
{
|
||||||
|
if (0 == arguments.size())
|
||||||
|
throw Exception("-Array aggregate functions require at least one argument", ErrorCodes::NUMBER_OF_ARGUMENTS_DOESNT_MATCH);
|
||||||
|
|
||||||
DataTypes nested_arguments;
|
DataTypes nested_arguments;
|
||||||
for (const auto & type : arguments)
|
for (const auto & type : arguments)
|
||||||
{
|
{
|
||||||
|
@ -377,6 +377,7 @@ namespace ErrorCodes
|
|||||||
extern const int CANNOT_STAT = 400;
|
extern const int CANNOT_STAT = 400;
|
||||||
extern const int FEATURE_IS_NOT_ENABLED_AT_BUILD_TIME = 401;
|
extern const int FEATURE_IS_NOT_ENABLED_AT_BUILD_TIME = 401;
|
||||||
extern const int CANNOT_IOSETUP = 402;
|
extern const int CANNOT_IOSETUP = 402;
|
||||||
|
extern const int INVALID_JOIN_ON_EXPRESSION = 403;
|
||||||
|
|
||||||
|
|
||||||
extern const int KEEPER_EXCEPTION = 999;
|
extern const int KEEPER_EXCEPTION = 999;
|
||||||
|
@ -1011,10 +1011,11 @@ public:
|
|||||||
DataTypePtr observed_type0 = removeNullable(array_type->getNestedType());
|
DataTypePtr observed_type0 = removeNullable(array_type->getNestedType());
|
||||||
DataTypePtr observed_type1 = removeNullable(arguments[1]);
|
DataTypePtr observed_type1 = removeNullable(arguments[1]);
|
||||||
|
|
||||||
if (!(observed_type0->isNumber() && observed_type1->isNumber())
|
/// We also support arrays of Enum type (that are represented by number) to search numeric values.
|
||||||
|
if (!(observed_type0->isValueRepresentedByNumber() && observed_type1->isNumber())
|
||||||
&& !observed_type0->equals(*observed_type1))
|
&& !observed_type0->equals(*observed_type1))
|
||||||
throw Exception("Types of array and 2nd argument of function "
|
throw Exception("Types of array and 2nd argument of function "
|
||||||
+ getName() + " must be identical up to nullability. Passed: "
|
+ getName() + " must be identical up to nullability or numeric types or Enum and numeric type. Passed: "
|
||||||
+ arguments[0]->getName() + " and " + arguments[1]->getName() + ".",
|
+ arguments[0]->getName() + " and " + arguments[1]->getName() + ".",
|
||||||
ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT);
|
ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT);
|
||||||
}
|
}
|
||||||
|
@ -61,6 +61,7 @@
|
|||||||
#include <DataTypes/DataTypeFunction.h>
|
#include <DataTypes/DataTypeFunction.h>
|
||||||
#include <Functions/FunctionsMiscellaneous.h>
|
#include <Functions/FunctionsMiscellaneous.h>
|
||||||
#include <DataTypes/DataTypeTuple.h>
|
#include <DataTypes/DataTypeTuple.h>
|
||||||
|
#include <Parsers/queryToString.h>
|
||||||
|
|
||||||
|
|
||||||
namespace DB
|
namespace DB
|
||||||
@ -89,6 +90,7 @@ namespace ErrorCodes
|
|||||||
extern const int NUMBER_OF_ARGUMENTS_DOESNT_MATCH;
|
extern const int NUMBER_OF_ARGUMENTS_DOESNT_MATCH;
|
||||||
extern const int CONDITIONAL_TREE_PARENT_NOT_FOUND;
|
extern const int CONDITIONAL_TREE_PARENT_NOT_FOUND;
|
||||||
extern const int TYPE_MISMATCH;
|
extern const int TYPE_MISMATCH;
|
||||||
|
extern const int INVALID_JOIN_ON_EXPRESSION;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -2856,22 +2858,53 @@ void ExpressionAnalyzer::collectJoinedColumns(NameSet & joined_columns, NamesAnd
|
|||||||
nested_result_sample = InterpreterSelectWithUnionQuery::getSampleBlock(subquery, context);
|
nested_result_sample = InterpreterSelectWithUnionQuery::getSampleBlock(subquery, context);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
auto add_name_to_join_keys = [](Names & join_keys, const String & name, const char * where)
|
||||||
|
{
|
||||||
|
if (join_keys.end() == std::find(join_keys.begin(), join_keys.end(), name))
|
||||||
|
join_keys.push_back(name);
|
||||||
|
else
|
||||||
|
throw Exception("Duplicate column " + name + " " + where, ErrorCodes::DUPLICATE_COLUMN);
|
||||||
|
};
|
||||||
|
|
||||||
if (table_join.using_expression_list)
|
if (table_join.using_expression_list)
|
||||||
{
|
{
|
||||||
auto & keys = typeid_cast<ASTExpressionList &>(*table_join.using_expression_list);
|
auto & keys = typeid_cast<ASTExpressionList &>(*table_join.using_expression_list);
|
||||||
for (const auto & key : keys.children)
|
for (const auto & key : keys.children)
|
||||||
{
|
{
|
||||||
if (join_key_names_left.end() == std::find(join_key_names_left.begin(), join_key_names_left.end(), key->getColumnName()))
|
add_name_to_join_keys(join_key_names_left, key->getColumnName(), "in USING list");
|
||||||
join_key_names_left.push_back(key->getColumnName());
|
add_name_to_join_keys(join_key_names_right, key->getAliasOrColumnName(), "in USING list");
|
||||||
else
|
|
||||||
throw Exception("Duplicate column " + key->getColumnName() + " in USING list", ErrorCodes::DUPLICATE_COLUMN);
|
|
||||||
|
|
||||||
if (join_key_names_right.end() == std::find(join_key_names_right.begin(), join_key_names_right.end(), key->getAliasOrColumnName()))
|
|
||||||
join_key_names_right.push_back(key->getAliasOrColumnName());
|
|
||||||
else
|
|
||||||
throw Exception("Duplicate column " + key->getAliasOrColumnName() + " in USING list", ErrorCodes::DUPLICATE_COLUMN);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else if (table_join.on_expression)
|
||||||
|
{
|
||||||
|
const auto supported_syntax =
|
||||||
|
"\nSupported syntax: JOIN ON [table.]column = [table.]column [AND [table.]column = [table.]column ...]";
|
||||||
|
auto throwSyntaxException = [&](const String & msg)
|
||||||
|
{
|
||||||
|
throw Exception("Invalid expression for JOIN ON. " + msg + supported_syntax, ErrorCodes::INVALID_JOIN_ON_EXPRESSION);
|
||||||
|
};
|
||||||
|
|
||||||
|
auto add_columns_from_equals_expr = [&](const ASTPtr & expr)
|
||||||
|
{
|
||||||
|
auto * func_equals = typeid_cast<const ASTFunction *>(expr.get());
|
||||||
|
if (!func_equals || func_equals->name != "equals")
|
||||||
|
throwSyntaxException("Expected equals expression, got " + queryToString(expr));
|
||||||
|
|
||||||
|
String left_name = func_equals->arguments->children.at(0)->getAliasOrColumnName();
|
||||||
|
String right_name = func_equals->arguments->children.at(1)->getAliasOrColumnName();
|
||||||
|
add_name_to_join_keys(join_key_names_left, left_name, "in JOIN ON expression for left table");
|
||||||
|
add_name_to_join_keys(join_key_names_right, right_name, "in JOIN ON expression for right table");
|
||||||
|
};
|
||||||
|
|
||||||
|
auto * func = typeid_cast<const ASTFunction *>(table_join.on_expression.get());
|
||||||
|
if (func && func->name == "and")
|
||||||
|
{
|
||||||
|
for (auto expr : func->children)
|
||||||
|
add_columns_from_equals_expr(expr);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
add_columns_from_equals_expr(table_join.on_expression);
|
||||||
|
}
|
||||||
|
|
||||||
for (const auto i : ext::range(0, nested_result_sample.columns()))
|
for (const auto i : ext::range(0, nested_result_sample.columns()))
|
||||||
{
|
{
|
||||||
|
@ -428,5 +428,7 @@ SELECT COVAR_SAMPArray([CAST( 0 AS Int8)],arrayPopBack([CAST( 0 AS Int8)]));
|
|||||||
SELECT medianTimingWeightedArray([CAST( 0 AS Int8)],arrayPopBack([CAST( 0 AS Int8)]));
|
SELECT medianTimingWeightedArray([CAST( 0 AS Int8)],arrayPopBack([CAST( 0 AS Int8)]));
|
||||||
SELECT quantilesDeterministicArray([CAST( 0 AS Int8)],arrayPopBack([CAST( 0 AS Int32)]));
|
SELECT quantilesDeterministicArray([CAST( 0 AS Int8)],arrayPopBack([CAST( 0 AS Int32)]));
|
||||||
|
|
||||||
SELECT maxIntersections([], [])
|
SELECT maxIntersections([], []);
|
||||||
SELECT sumMap([], [])
|
SELECT sumMap([], []);
|
||||||
|
|
||||||
|
SELECT countArray();
|
||||||
|
Loading…
Reference in New Issue
Block a user