Function bitPositionsToArray added support for big integers

This commit is contained in:
Maksim Kita 2021-06-17 22:32:39 +03:00
parent 6d44aa3034
commit ca672b0a0d
3 changed files with 56 additions and 5 deletions

View File

@ -1523,7 +1523,7 @@ public:
DataTypePtr getReturnTypeImpl(const DataTypes & arguments) const override DataTypePtr getReturnTypeImpl(const DataTypes & arguments) const override
{ {
if (!isNativeInteger(arguments[0])) if (!isInteger(arguments[0]))
throw Exception(ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT, throw Exception(ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT,
"Illegal type {} of argument of function {}", "Illegal type {} of argument of function {}",
getName(), getName(),
@ -1553,15 +1553,32 @@ public:
result_array_values_data.reserve(size * 2); result_array_values_data.reserve(size * 2);
using UnsignedType = make_unsigned_t<T>; using UnsignedType = make_unsigned_t<T>;
for (size_t row = 0; row < size; ++row) for (size_t row = 0; row < size; ++row)
{ {
UnsignedType x = static_cast<UnsignedType>(vec_from[row]); UnsignedType x = static_cast<UnsignedType>(vec_from[row]);
if constexpr (is_big_int_v<UnsignedType>)
{
size_t position = 0;
while (x)
{
if (x & 1)
result_array_values_data.push_back(position);
x >>= 1;
++position;
}
}
else
{
while (x) while (x)
{ {
result_array_values_data.push_back(getTrailingZeroBitsUnsafe(x)); result_array_values_data.push_back(getTrailingZeroBitsUnsafe(x));
x &= (x - 1); x &= (x - 1);
} }
}
result_array_offsets_data[row] = result_array_values_data.size(); result_array_offsets_data[row] = result_array_values_data.size();
} }
@ -1581,10 +1598,14 @@ public:
|| (result_column = executeType<UInt32>(in_column)) || (result_column = executeType<UInt32>(in_column))
|| (result_column = executeType<UInt32>(in_column)) || (result_column = executeType<UInt32>(in_column))
|| (result_column = executeType<UInt64>(in_column)) || (result_column = executeType<UInt64>(in_column))
|| (result_column = executeType<UInt128>(in_column))
|| (result_column = executeType<UInt256>(in_column))
|| (result_column = executeType<Int8>(in_column)) || (result_column = executeType<Int8>(in_column))
|| (result_column = executeType<Int16>(in_column)) || (result_column = executeType<Int16>(in_column))
|| (result_column = executeType<Int32>(in_column)) || (result_column = executeType<Int32>(in_column))
|| (result_column = executeType<Int64>(in_column)))) || (result_column = executeType<Int64>(in_column))
|| (result_column = executeType<Int128>(in_column))
|| (result_column = executeType<Int256>(in_column))))
{ {
throw Exception(ErrorCodes::ILLEGAL_COLUMN, throw Exception(ErrorCodes::ILLEGAL_COLUMN,
"Illegal column {} of first argument of function {}", "Illegal column {} of first argument of function {}",

View File

@ -16,6 +16,12 @@ Int32
Int64 Int64
0 [] 0 []
1 [0] 1 [0]
Int128
0 []
1 [0]
Int256
0 []
1 [0]
UInt8 UInt8
0 [] 0 []
1 [0] 1 [0]
@ -29,3 +35,10 @@ UInt32
UInt64 UInt64
0 [] 0 []
1 [0] 1 [0]
UInt128
0 []
1 [0]
340282366920938463463374607431768211455 [0]
UInt256
0 []
1 [0]

View File

@ -20,6 +20,14 @@ SELECT 'Int64';
SELECT toInt64(0), bitPositionsToArray(toInt64(0)); SELECT toInt64(0), bitPositionsToArray(toInt64(0));
SELECT toInt64(1), bitPositionsToArray(toInt64(1)); SELECT toInt64(1), bitPositionsToArray(toInt64(1));
SELECT 'Int128';
SELECT toInt128(0), bitPositionsToArray(toInt128(0));
SELECT toInt128(1), bitPositionsToArray(toInt128(1));
SELECT 'Int256';
SELECT toInt256(0), bitPositionsToArray(toInt256(0));
SELECT toInt256(1), bitPositionsToArray(toInt256(1));
SELECT 'UInt8'; SELECT 'UInt8';
SELECT toUInt8(0), bitPositionsToArray(toUInt8(0)); SELECT toUInt8(0), bitPositionsToArray(toUInt8(0));
SELECT toUInt8(1), bitPositionsToArray(toUInt8(1)); SELECT toUInt8(1), bitPositionsToArray(toUInt8(1));
@ -36,3 +44,12 @@ SELECT toUInt32(1), bitPositionsToArray(toUInt32(1));
SELECT 'UInt64'; SELECT 'UInt64';
SELECT toUInt64(0), bitPositionsToArray(toUInt64(0)); SELECT toUInt64(0), bitPositionsToArray(toUInt64(0));
SELECT toUInt64(1), bitPositionsToArray(toUInt64(1)); SELECT toUInt64(1), bitPositionsToArray(toUInt64(1));
SELECT 'UInt128';
SELECT toUInt128(0), bitPositionsToArray(toUInt128(0));
SELECT toUInt128(1), bitPositionsToArray(toUInt128(1));
SELECT toUInt128(-1), bitPositionsToArray(toUInt128(1));
SELECT 'UInt256';
SELECT toUInt256(0), bitPositionsToArray(toUInt256(0));
SELECT toUInt256(1), bitPositionsToArray(toUInt256(1));