1#include <DataTypes/DataTypeDecimalBase.h>
2
3#include <Common/assert_cast.h>
4#include <Common/typeid_cast.h>
5#include <Core/DecimalFunctions.h>
6#include <DataTypes/DataTypeFactory.h>
7#include <Formats/ProtobufReader.h>
8#include <Formats/ProtobufWriter.h>
9#include <IO/ReadHelpers.h>
10#include <IO/WriteHelpers.h>
11#include <IO/readDecimalText.h>
12#include <Interpreters/Context.h>
13#include <Parsers/ASTLiteral.h>
14#include <Parsers/IAST.h>
15
16#include <type_traits>
17
18namespace DB
19{
20
21namespace ErrorCodes
22{
23 extern const int NUMBER_OF_ARGUMENTS_DOESNT_MATCH;
24 extern const int ILLEGAL_TYPE_OF_ARGUMENT;
25 extern const int ARGUMENT_OUT_OF_BOUND;
26}
27
28
29bool decimalCheckComparisonOverflow(const Context & context) { return context.getSettingsRef().decimal_check_overflow; }
30bool decimalCheckArithmeticOverflow(const Context & context) { return context.getSettingsRef().decimal_check_overflow; }
31
32template <typename T>
33Field DataTypeDecimalBase<T>::getDefault() const
34{
35 return DecimalField(T(0), scale);
36}
37
38template <typename T>
39MutableColumnPtr DataTypeDecimalBase<T>::createColumn() const
40{
41 return ColumnType::create(0, scale);
42}
43
44template <typename T>
45void DataTypeDecimalBase<T>::serializeBinary(const Field & field, WriteBuffer & ostr) const
46{
47 FieldType x = get<DecimalField<T>>(field);
48 writeBinary(x, ostr);
49}
50
51template <typename T>
52void DataTypeDecimalBase<T>::serializeBinary(const IColumn & column, size_t row_num, WriteBuffer & ostr) const
53{
54 const FieldType & x = assert_cast<const ColumnType &>(column).getElement(row_num);
55 writeBinary(x, ostr);
56}
57
58template <typename T>
59void DataTypeDecimalBase<T>::serializeBinaryBulk(const IColumn & column, WriteBuffer & ostr, size_t offset, size_t limit) const
60{
61 const typename ColumnType::Container & x = typeid_cast<const ColumnType &>(column).getData();
62
63 size_t size = x.size();
64
65 if (limit == 0 || offset + limit > size)
66 limit = size - offset;
67
68 ostr.write(reinterpret_cast<const char *>(&x[offset]), sizeof(FieldType) * limit);
69}
70
71template <typename T>
72void DataTypeDecimalBase<T>::deserializeBinary(Field & field, ReadBuffer & istr) const
73{
74 typename FieldType::NativeType x;
75 readBinary(x, istr);
76 field = DecimalField(T(x), this->scale);
77}
78
79template <typename T>
80void DataTypeDecimalBase<T>::deserializeBinary(IColumn & column, ReadBuffer & istr) const
81{
82 typename FieldType::NativeType x;
83 readBinary(x, istr);
84 assert_cast<ColumnType &>(column).getData().push_back(FieldType(x));
85}
86
87template <typename T>
88void DataTypeDecimalBase<T>::deserializeBinaryBulk(IColumn & column, ReadBuffer & istr, size_t limit, double) const
89{
90 typename ColumnType::Container & x = typeid_cast<ColumnType &>(column).getData();
91 size_t initial_size = x.size();
92 x.resize(initial_size + limit);
93 size_t size = istr.readBig(reinterpret_cast<char*>(&x[initial_size]), sizeof(FieldType) * limit);
94 x.resize(initial_size + size / sizeof(FieldType));
95}
96
97template <typename T>
98T DataTypeDecimalBase<T>::getScaleMultiplier(UInt32 scale_)
99{
100 return DecimalUtils::scaleMultiplier<typename T::NativeType>(scale_);
101}
102
103
104/// Explicit template instantiations.
105template class DataTypeDecimalBase<Decimal32>;
106template class DataTypeDecimalBase<Decimal64>;
107template class DataTypeDecimalBase<Decimal128>;
108
109}
110