mirror of
https://github.com/ClickHouse/ClickHouse.git
synced 2024-11-23 08:02:02 +00:00
Introduce default parameters to DECIMAL family types
In standard SQL, the syntax DECIMAL(M) is equivalent to DECIMAL(M,0). Similarly, the syntax DECIMAL is equivalent to DECIMAL(M,0), where the implementation is permitted to decide the value of M. https://dev.mysql.com/doc/refman/8.0/en/fixed-point-types.html Since MySQL uses 10 as the default value for precision, suggesting to also support this in ClickHouse
This commit is contained in:
parent
525cc46b0b
commit
15310117b0
@ -4,15 +4,17 @@ sidebar_position: 42
|
||||
sidebar_label: Decimal
|
||||
---
|
||||
|
||||
# Decimal(P, S), Decimal32(S), Decimal64(S), Decimal128(S), Decimal256(S)
|
||||
# Decimal, Decimal(P), Decimal(P, S), Decimal32(S), Decimal64(S), Decimal128(S), Decimal256(S)
|
||||
|
||||
Signed fixed-point numbers that keep precision during add, subtract and multiply operations. For division least significant digits are discarded (not rounded).
|
||||
|
||||
## Parameters
|
||||
|
||||
- P - precision. Valid range: \[ 1 : 76 \]. Determines how many decimal digits number can have (including fraction).
|
||||
- P - precision. Valid range: \[ 1 : 76 \]. Determines how many decimal digits number can have (including fraction). By default the precision is 10.
|
||||
- S - scale. Valid range: \[ 0 : P \]. Determines how many decimal digits fraction can have.
|
||||
|
||||
Decimal(P) is equivalent to Decimal(P, 0). Similarly, the syntax Decimal is equivalent to Decimal(10, 0).
|
||||
|
||||
Depending on P parameter value Decimal(P, S) is a synonym for:
|
||||
- P from \[ 1 : 9 \] - for Decimal32(S)
|
||||
- P from \[ 10 : 18 \] - for Decimal64(S)
|
||||
|
@ -74,21 +74,30 @@ SerializationPtr DataTypeDecimal<T>::doGetDefaultSerialization() const
|
||||
|
||||
static DataTypePtr create(const ASTPtr & arguments)
|
||||
{
|
||||
if (!arguments || arguments->children.size() != 2)
|
||||
throw Exception(ErrorCodes::NUMBER_OF_ARGUMENTS_DOESNT_MATCH,
|
||||
"Decimal data type family must have exactly two arguments: precision and scale");
|
||||
UInt64 precision = 10;
|
||||
UInt64 scale = 0;
|
||||
if (arguments)
|
||||
{
|
||||
if (arguments->children.empty() || arguments->children.size() > 2)
|
||||
throw Exception(
|
||||
ErrorCodes::NUMBER_OF_ARGUMENTS_DOESNT_MATCH,
|
||||
"Decimal data type family must have precision and optional scale arguments");
|
||||
|
||||
const auto * precision = arguments->children[0]->as<ASTLiteral>();
|
||||
const auto * scale = arguments->children[1]->as<ASTLiteral>();
|
||||
const auto * precision_arg = arguments->children[0]->as<ASTLiteral>();
|
||||
if (!precision_arg || precision_arg->value.getType() != Field::Types::UInt64)
|
||||
throw Exception(ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT, "Decimal argument precision is invalid");
|
||||
precision = precision_arg->value.get<UInt64>();
|
||||
|
||||
if (!precision || precision->value.getType() != Field::Types::UInt64 ||
|
||||
!scale || !(scale->value.getType() == Field::Types::Int64 || scale->value.getType() == Field::Types::UInt64))
|
||||
throw Exception(ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT, "Decimal data type family must have two numbers as its arguments");
|
||||
if (arguments->children.size() == 2)
|
||||
{
|
||||
const auto * scale_arg = arguments->children[1]->as<ASTLiteral>();
|
||||
if (!scale_arg || !isInt64OrUInt64FieldType(scale_arg->value.getType()))
|
||||
throw Exception(ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT, "Decimal argument scale is invalid");
|
||||
scale = scale_arg->value.get<UInt64>();
|
||||
}
|
||||
}
|
||||
|
||||
UInt64 precision_value = precision->value.get<UInt64>();
|
||||
UInt64 scale_value = scale->value.get<UInt64>();
|
||||
|
||||
return createDecimal<DataTypeDecimal>(precision_value, scale_value);
|
||||
return createDecimal<DataTypeDecimal>(precision, scale);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
|
@ -0,0 +1,4 @@
|
||||
Decimal(9, 8)
|
||||
Decimal(18, 0)
|
||||
Decimal(10, 0)
|
||||
Decimal(18, 0) Decimal(10, 0)
|
@ -0,0 +1,19 @@
|
||||
DROP TABLE IF EXISTS decimal;
|
||||
|
||||
CREATE TABLE IF NOT EXISTS decimal
|
||||
(
|
||||
d1 DECIMAL(9, 8),
|
||||
d2 DECIMAL(18),
|
||||
d3 DECIMAL
|
||||
)
|
||||
ENGINE = MergeTree
|
||||
PARTITION BY toInt32(d1)
|
||||
ORDER BY (d2, d3);
|
||||
|
||||
INSERT INTO decimal (d1, d2, d3) VALUES (4.2, 4.2, 4.2);
|
||||
|
||||
SELECT type FROM system.columns WHERE table = 'decimal' AND database = currentDatabase();
|
||||
|
||||
SELECT toTypeName(d2), toTypeName(d3) FROM decimal LIMIT 1;
|
||||
|
||||
DROP TABLE decimal;
|
Loading…
Reference in New Issue
Block a user