mirror of
https://github.com/ClickHouse/ClickHouse.git
synced 2024-11-24 08:32:02 +00:00
some decimal field improvements CLICKHOUSE-3765
This commit is contained in:
parent
2e65f4922f
commit
53ec40eeee
@ -278,8 +278,17 @@ void ColumnVector<T>::getExtremes(Field & min, Field & max) const
|
||||
|
||||
if (size == 0)
|
||||
{
|
||||
min = typename NearestFieldType<T>::Type(0);
|
||||
max = typename NearestFieldType<T>::Type(0);
|
||||
if constexpr (IsDecimalNumber<T>)
|
||||
{
|
||||
min = typename NearestFieldType<T>::Type(0, data.getScale());
|
||||
max = typename NearestFieldType<T>::Type(0, data.getScale());
|
||||
}
|
||||
else
|
||||
{
|
||||
min = typename NearestFieldType<T>::Type(0);
|
||||
max = typename NearestFieldType<T>::Type(0);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
@ -313,8 +322,16 @@ void ColumnVector<T>::getExtremes(Field & min, Field & max) const
|
||||
cur_max = x;
|
||||
}
|
||||
|
||||
min = typename NearestFieldType<T>::Type(cur_min);
|
||||
max = typename NearestFieldType<T>::Type(cur_max);
|
||||
if constexpr (IsDecimalNumber<T>)
|
||||
{
|
||||
min = typename NearestFieldType<T>::Type(cur_min, data.getScale());
|
||||
max = typename NearestFieldType<T>::Type(cur_max, data.getScale());
|
||||
}
|
||||
else
|
||||
{
|
||||
min = typename NearestFieldType<T>::Type(cur_min);
|
||||
max = typename NearestFieldType<T>::Type(cur_max);
|
||||
}
|
||||
}
|
||||
|
||||
/// Explicit template instantiations - to avoid code bloat in headers.
|
||||
|
@ -38,7 +38,7 @@ class DecimalField
|
||||
public:
|
||||
static constexpr UInt32 wrongScale() { return std::numeric_limits<UInt32>::max(); }
|
||||
|
||||
DecimalField(T value, UInt32 scale_ = wrongScale())
|
||||
DecimalField(T value, UInt32 scale_)
|
||||
: dec(value),
|
||||
scale(scale_)
|
||||
{}
|
||||
|
@ -76,11 +76,17 @@ const ColumnConst * checkAndGetColumnConstStringOrFixedString(const IColumn * co
|
||||
|
||||
/// Transform anything to Field.
|
||||
template <typename T>
|
||||
inline Field toField(const T & x)
|
||||
inline std::enable_if_t<!IsDecimalNumber<T>, Field> toField(const T & x)
|
||||
{
|
||||
return Field(typename NearestFieldType<T>::Type(x));
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
inline std::enable_if_t<IsDecimalNumber<T>, Field> toField(const T & x, UInt32 scale)
|
||||
{
|
||||
return Field(typename NearestFieldType<T>::Type(x, scale));
|
||||
}
|
||||
|
||||
|
||||
Columns convertConstTupleToConstantElements(const ColumnConst & column);
|
||||
|
||||
|
@ -1227,14 +1227,16 @@ public:
|
||||
auto res = OpImpl::constant_constant(
|
||||
col_left->template getValue<T0>(), col_right->template getValue<T1>(), scale_a, scale_b);
|
||||
block.getByPosition(result).column =
|
||||
ResultDataType(type.getPrecision(), type.getScale()).createColumnConst(col_left->size(), toField(res));
|
||||
ResultDataType(type.getPrecision(), type.getScale()).createColumnConst(
|
||||
col_left->size(), toField(res, type.getScale()));
|
||||
}
|
||||
else
|
||||
{
|
||||
auto res = OpImpl::XOverflow::constant_constant(
|
||||
col_left->template getValue<T0>(), col_right->template getValue<T1>(), scale_a, scale_b);
|
||||
block.getByPosition(result).column =
|
||||
ResultDataType(type.getPrecision(), type.getScale()).createColumnConst(col_left->size(), toField(res));
|
||||
ResultDataType(type.getPrecision(), type.getScale()).createColumnConst(
|
||||
col_left->size(), toField(res, type.getScale()));
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -84,7 +84,7 @@ static Field convertIntToDecimalType(const Field & from, const To & type)
|
||||
throw Exception("Number is too much to place in " + type.getName(), ErrorCodes::ARGUMENT_OUT_OF_BOUND);
|
||||
|
||||
FieldType scaled_value = type.getScaleMultiplier() * value;
|
||||
return Field(typename NearestFieldType<FieldType>::Type(scaled_value));
|
||||
return Field(typename NearestFieldType<FieldType>::Type(scaled_value, type.getScale()));
|
||||
}
|
||||
|
||||
|
||||
@ -95,7 +95,7 @@ static Field convertStringToDecimalType(const Field & from, const DataTypeDecima
|
||||
|
||||
const String & str_value = from.get<String>();
|
||||
T value = type.parseFromString(str_value);
|
||||
return Field(typename NearestFieldType<FieldType>::Type(value));
|
||||
return Field(typename NearestFieldType<FieldType>::Type(value, type.getScale()));
|
||||
}
|
||||
|
||||
|
||||
|
21
dbms/tests/queries/0_stateless/00700_decimal_in_keys.sql
Normal file
21
dbms/tests/queries/0_stateless/00700_decimal_in_keys.sql
Normal file
@ -0,0 +1,21 @@
|
||||
SET allow_experimental_decimal_type = 1;
|
||||
CREATE DATABASE IF NOT EXISTS test;
|
||||
DROP TABLE IF EXISTS test.decimal;
|
||||
|
||||
CREATE TABLE IF NOT EXISTS test.decimal
|
||||
(
|
||||
d1 DECIMAL(9, 8),
|
||||
d2 DECIMAL(18, 8),
|
||||
d3 DECIMAL(38, 8)
|
||||
)
|
||||
ENGINE = MergeTree
|
||||
PARTITION BY toInt32(d1)
|
||||
ORDER BY (d2, d3);
|
||||
|
||||
INSERT INTO test.decimal (d1, d2, d3)
|
||||
SELECT toDecimal32(number % 10, 8), toDecimal64(number, 8), toDecimal128(number, 8) FROM system.numbers LIMIT 50;
|
||||
|
||||
SELECT count() FROM test.decimal WHERE d1 = 1;
|
||||
--SELECT * FROM test.decimal WHERE d1 <= toDecimal32(2, 8) ORDER BY d2 DESC;
|
||||
|
||||
DROP TABLE test.decimal;
|
Loading…
Reference in New Issue
Block a user