diff --git a/cpp/src/arrow/array/array_decimal.cc b/cpp/src/arrow/array/array_decimal.cc index d65f6ee5356..d41b1185fe2 100644 --- a/cpp/src/arrow/array/array_decimal.cc +++ b/cpp/src/arrow/array/array_decimal.cc @@ -32,32 +32,21 @@ namespace arrow { using internal::checked_cast; -// ---------------------------------------------------------------------- -// Decimal128 -Decimal128Array::Decimal128Array(const std::shared_ptr& data) +template +BaseDecimalArray::BaseDecimalArray(const std::shared_ptr& data) : FixedSizeBinaryArray(data) { - ARROW_CHECK_EQ(data->type->id(), Type::DECIMAL128); + ARROW_CHECK_EQ(data->type->id(), DecimalTypeTraits::Id); } -std::string Decimal128Array::FormatValue(int64_t i) const { - const auto& type_ = checked_cast(*type()); - const Decimal128 value(GetValue(i)); +template +std::string BaseDecimalArray::FormatValue(int64_t i) const { + const auto& type_ = checked_cast::TypeClass&>(*type()); + const typename DecimalTypeTraits::ValueType value(GetValue(i)); return value.ToString(type_.scale()); } -// ---------------------------------------------------------------------- -// Decimal256 - -Decimal256Array::Decimal256Array(const std::shared_ptr& data) - : FixedSizeBinaryArray(data) { - ARROW_CHECK_EQ(data->type->id(), Type::DECIMAL256); -} - -std::string Decimal256Array::FormatValue(int64_t i) const { - const auto& type_ = checked_cast(*type()); - const Decimal256 value(GetValue(i)); - return value.ToString(type_.scale()); -} +template class BaseDecimalArray<128>; +template class BaseDecimalArray<256>; } // namespace arrow diff --git a/cpp/src/arrow/array/array_decimal.h b/cpp/src/arrow/array/array_decimal.h index 8d7d1c59cd0..621bdd4d9cd 100644 --- a/cpp/src/arrow/array/array_decimal.h +++ b/cpp/src/arrow/array/array_decimal.h @@ -22,45 +22,39 @@ #include #include "arrow/array/array_binary.h" +#include "arrow/util/decimal_type_traits.h" #include "arrow/array/data.h" #include "arrow/type.h" #include "arrow/util/visibility.h" namespace arrow { -// ---------------------------------------------------------------------- -// Decimal128Array - -/// Concrete Array class for 128-bit decimal data -class ARROW_EXPORT Decimal128Array : public FixedSizeBinaryArray { +/// Template Array class for decimal data +template +class BaseDecimalArray : public FixedSizeBinaryArray { public: - using TypeClass = Decimal128Type; + using TypeClass = typename DecimalTypeTraits::TypeClass; using FixedSizeBinaryArray::FixedSizeBinaryArray; - /// \brief Construct Decimal128Array from ArrayData instance - explicit Decimal128Array(const std::shared_ptr& data); + /// \brief Construct DecimalArray from ArrayData instance + explicit BaseDecimalArray(const std::shared_ptr& data); std::string FormatValue(int64_t i) const; }; -// Backward compatibility -using DecimalArray = Decimal128Array; - -// ---------------------------------------------------------------------- -// Decimal256Array - -/// Concrete Array class for 256-bit decimal data -class ARROW_EXPORT Decimal256Array : public FixedSizeBinaryArray { - public: - using TypeClass = Decimal256Type; +/// Array class for decimal 128-bit data +class ARROW_EXPORT Decimal128Array : public BaseDecimalArray<128> { + using BaseDecimalArray<128>::BaseDecimalArray; +}; - using FixedSizeBinaryArray::FixedSizeBinaryArray; +/// Array class for decimal 256-bit data +class ARROW_EXPORT Decimal256Array : public BaseDecimalArray<256> { + using BaseDecimalArray<256>::BaseDecimalArray; +}; - /// \brief Construct Decimal256Array from ArrayData instance - explicit Decimal256Array(const std::shared_ptr& data); +// Backward compatibility +using DecimalArray = Decimal128Array; - std::string FormatValue(int64_t i) const; -}; } // namespace arrow diff --git a/cpp/src/arrow/array/builder_decimal.cc b/cpp/src/arrow/array/builder_decimal.cc index 18ec06c24c7..712b9221256 100644 --- a/cpp/src/arrow/array/builder_decimal.cc +++ b/cpp/src/arrow/array/builder_decimal.cc @@ -33,30 +33,35 @@ class Buffer; class MemoryPool; // ---------------------------------------------------------------------- -// Decimal128Builder +// BaseDecimalBuilder -Decimal128Builder::Decimal128Builder(const std::shared_ptr& type, +template +BaseDecimalBuilder::BaseDecimalBuilder(const std::shared_ptr& type, MemoryPool* pool) : FixedSizeBinaryBuilder(type, pool), - decimal_type_(internal::checked_pointer_cast(type)) {} + decimal_type_(internal::checked_pointer_cast::TypeClass>(type)) {} -Status Decimal128Builder::Append(Decimal128 value) { +template +Status BaseDecimalBuilder::Append(typename DecimalTypeTraits::ValueType value) { RETURN_NOT_OK(FixedSizeBinaryBuilder::Reserve(1)); UnsafeAppend(value); return Status::OK(); } -void Decimal128Builder::UnsafeAppend(Decimal128 value) { +template +void BaseDecimalBuilder::UnsafeAppend(typename DecimalTypeTraits::ValueType value) { value.ToBytes(GetMutableValue(length())); - byte_builder_.UnsafeAdvance(16); + byte_builder_.UnsafeAdvance((width >> 3)); UnsafeAppendToBitmap(true); } -void Decimal128Builder::UnsafeAppend(util::string_view value) { +template +void BaseDecimalBuilder::UnsafeAppend(util::string_view value) { FixedSizeBinaryBuilder::UnsafeAppend(value); } -Status Decimal128Builder::FinishInternal(std::shared_ptr* out) { +template +Status BaseDecimalBuilder::FinishInternal(std::shared_ptr* out) { std::shared_ptr data; RETURN_NOT_OK(byte_builder_.Finish(&data)); std::shared_ptr null_bitmap; @@ -67,39 +72,8 @@ Status Decimal128Builder::FinishInternal(std::shared_ptr* out) { return Status::OK(); } -// ---------------------------------------------------------------------- -// Decimal256Builder - -Decimal256Builder::Decimal256Builder(const std::shared_ptr& type, - MemoryPool* pool) - : FixedSizeBinaryBuilder(type, pool), - decimal_type_(internal::checked_pointer_cast(type)) {} - -Status Decimal256Builder::Append(Decimal256 value) { - RETURN_NOT_OK(FixedSizeBinaryBuilder::Reserve(1)); - UnsafeAppend(value); - return Status::OK(); -} - -void Decimal256Builder::UnsafeAppend(Decimal256 value) { - value.ToBytes(GetMutableValue(length())); - byte_builder_.UnsafeAdvance(32); - UnsafeAppendToBitmap(true); -} - -void Decimal256Builder::UnsafeAppend(util::string_view value) { - FixedSizeBinaryBuilder::UnsafeAppend(value); -} - -Status Decimal256Builder::FinishInternal(std::shared_ptr* out) { - std::shared_ptr data; - RETURN_NOT_OK(byte_builder_.Finish(&data)); - std::shared_ptr null_bitmap; - RETURN_NOT_OK(null_bitmap_builder_.Finish(&null_bitmap)); - - *out = ArrayData::Make(type(), length_, {null_bitmap, data}, null_count_); - capacity_ = length_ = null_count_ = 0; - return Status::OK(); -} +// Instantiate template classes to have methods of it +template class BaseDecimalBuilder<128>; +template class BaseDecimalBuilder<256>; } // namespace arrow diff --git a/cpp/src/arrow/array/builder_decimal.h b/cpp/src/arrow/array/builder_decimal.h index 31d81efb09f..6e539fda782 100644 --- a/cpp/src/arrow/array/builder_decimal.h +++ b/cpp/src/arrow/array/builder_decimal.h @@ -23,25 +23,27 @@ #include "arrow/array/builder_base.h" #include "arrow/array/builder_binary.h" #include "arrow/array/data.h" +#include "arrow/util/decimal_type_traits.h" #include "arrow/status.h" #include "arrow/type.h" #include "arrow/util/visibility.h" namespace arrow { -class ARROW_EXPORT Decimal128Builder : public FixedSizeBinaryBuilder { - public: - using TypeClass = Decimal128Type; +template +class BaseDecimalBuilder : public FixedSizeBinaryBuilder { +public: + using TypeClass = typename DecimalTypeTraits::TypeClass; - explicit Decimal128Builder(const std::shared_ptr& type, - MemoryPool* pool = default_memory_pool()); + explicit BaseDecimalBuilder(const std::shared_ptr& type, + MemoryPool* pool = default_memory_pool()); using FixedSizeBinaryBuilder::Append; using FixedSizeBinaryBuilder::AppendValues; using FixedSizeBinaryBuilder::Reset; - Status Append(Decimal128 val); - void UnsafeAppend(Decimal128 val); + Status Append(typename DecimalTypeTraits::ValueType val); + void UnsafeAppend(typename DecimalTypeTraits::ValueType val); void UnsafeAppend(util::string_view val); Status FinishInternal(std::shared_ptr* out) override; @@ -50,43 +52,25 @@ class ARROW_EXPORT Decimal128Builder : public FixedSizeBinaryBuilder { using ArrayBuilder::Finish; /// \endcond - Status Finish(std::shared_ptr* out) { return FinishTyped(out); } + Status Finish(std::shared_ptr::ArrayType>* out) { return FinishTyped(out); } std::shared_ptr type() const override { return decimal_type_; } protected: - std::shared_ptr decimal_type_; + std::shared_ptr::TypeClass> decimal_type_; }; -class ARROW_EXPORT Decimal256Builder : public FixedSizeBinaryBuilder { - public: - using TypeClass = Decimal256Type; - - explicit Decimal256Builder(const std::shared_ptr& type, - MemoryPool* pool = default_memory_pool()); - - using FixedSizeBinaryBuilder::Append; - using FixedSizeBinaryBuilder::AppendValues; - using FixedSizeBinaryBuilder::Reset; - - Status Append(Decimal256 val); - void UnsafeAppend(Decimal256 val); - void UnsafeAppend(util::string_view val); - - Status FinishInternal(std::shared_ptr* out) override; - - /// \cond FALSE - using ArrayBuilder::Finish; - /// \endcond - - Status Finish(std::shared_ptr* out) { return FinishTyped(out); } - - std::shared_ptr type() const override { return decimal_type_; } +/// Builder class for decimal 128-bit +class ARROW_EXPORT Decimal128Builder : public BaseDecimalBuilder<128> { + using BaseDecimalBuilder<128>::BaseDecimalBuilder; +}; - protected: - std::shared_ptr decimal_type_; +/// Builder class for decimal 128-bit +class ARROW_EXPORT Decimal256Builder : public BaseDecimalBuilder<256> { + using BaseDecimalBuilder<256>::BaseDecimalBuilder; }; +// Backward compatibility using DecimalBuilder = Decimal128Builder; } // namespace arrow diff --git a/cpp/src/arrow/scalar.h b/cpp/src/arrow/scalar.h index a6ec9d3afef..bb6500d419b 100644 --- a/cpp/src/arrow/scalar.h +++ b/cpp/src/arrow/scalar.h @@ -36,6 +36,7 @@ #include "arrow/type_traits.h" #include "arrow/util/compare.h" #include "arrow/util/decimal.h" +#include "arrow/util/decimal_type_traits.h" #include "arrow/util/string_view.h" #include "arrow/util/visibility.h" @@ -336,26 +337,24 @@ struct ARROW_EXPORT DurationScalar : public TemporalScalar { using TemporalScalar::TemporalScalar; }; -struct ARROW_EXPORT Decimal128Scalar : public Scalar { +template +struct BaseDecimalScalar : public Scalar { using Scalar::Scalar; - using TypeClass = Decimal128Type; - using ValueType = Decimal128; + using TypeClass = typename DecimalTypeTraits::TypeClass; + using ValueType = typename DecimalTypeTraits::ValueType; - Decimal128Scalar(Decimal128 value, std::shared_ptr type) + BaseDecimalScalar(ValueType value, std::shared_ptr type) : Scalar(std::move(type), true), value(value) {} - Decimal128 value; + ValueType value; }; -struct ARROW_EXPORT Decimal256Scalar : public Scalar { - using Scalar::Scalar; - using TypeClass = Decimal256Type; - using ValueType = Decimal256; - - Decimal256Scalar(Decimal256 value, std::shared_ptr type) - : Scalar(std::move(type), true), value(value) {} +struct ARROW_EXPORT Decimal128Scalar : public BaseDecimalScalar<128> { + using BaseDecimalScalar<128>::BaseDecimalScalar; +}; - Decimal256 value; +struct ARROW_EXPORT Decimal256Scalar : public BaseDecimalScalar<256> { + using BaseDecimalScalar<256>::BaseDecimalScalar; }; struct ARROW_EXPORT BaseListScalar : public Scalar { diff --git a/cpp/src/arrow/type.cc b/cpp/src/arrow/type.cc index f27f967c022..0b092b43a56 100644 --- a/cpp/src/arrow/type.cc +++ b/cpp/src/arrow/type.cc @@ -44,6 +44,7 @@ #include "arrow/util/make_unique.h" #include "arrow/util/range.h" #include "arrow/util/vector.h" +#include "arrow/util/decimal_type_traits.h" #include "arrow/visitor_inline.h" namespace arrow { @@ -748,35 +749,22 @@ std::vector> StructType::GetAllFieldsByName( } // ---------------------------------------------------------------------- -// Decimal128 type +// Decimal type -Decimal128Type::Decimal128Type(int32_t precision, int32_t scale) - : DecimalType(type_id, 16, precision, scale) { - ARROW_CHECK_GE(precision, kMinPrecision); - ARROW_CHECK_LE(precision, kMaxPrecision); -} -Result> Decimal128Type::Make(int32_t precision, int32_t scale) { - if (precision < kMinPrecision || precision > kMaxPrecision) { - return Status::Invalid("Decimal precision out of range: ", precision); - } - return std::make_shared(precision, scale); -} - -// ---------------------------------------------------------------------- -// Decimal256 type - -Decimal256Type::Decimal256Type(int32_t precision, int32_t scale) - : DecimalType(type_id, 32, precision, scale) { +template +BaseDecimalType::BaseDecimalType(int32_t precision, int32_t scale) + : DecimalType(DecimalTypeTraits::Id, (width >> 3), precision, scale) { ARROW_CHECK_GE(precision, kMinPrecision); ARROW_CHECK_LE(precision, kMaxPrecision); } -Result> Decimal256Type::Make(int32_t precision, int32_t scale) { +template +Result> BaseDecimalType::Make(int32_t precision, int32_t scale) { if (precision < kMinPrecision || precision > kMaxPrecision) { return Status::Invalid("Decimal precision out of range: ", precision); } - return std::make_shared(precision, scale); + return std::make_shared::TypeClass>(precision, scale); } // ---------------------------------------------------------------------- @@ -2169,16 +2157,14 @@ std::shared_ptr decimal256(int32_t precision, int32_t scale) { return std::make_shared(precision, scale); } -std::string Decimal128Type::ToString() const { +template +std::string BaseDecimalType::ToString() const { std::stringstream s; - s << "decimal(" << precision_ << ", " << scale_ << ")"; + s << type_name() << "(" << precision_ << ", " << scale_ << ")"; return s.str(); } -std::string Decimal256Type::ToString() const { - std::stringstream s; - s << "decimal256(" << precision_ << ", " << scale_ << ")"; - return s.str(); -} +template class BaseDecimalType<128>; +template class BaseDecimalType<256>; } // namespace arrow diff --git a/cpp/src/arrow/type.h b/cpp/src/arrow/type.h index c8a71ab9c13..f8284758193 100644 --- a/cpp/src/arrow/type.h +++ b/cpp/src/arrow/type.h @@ -33,6 +33,7 @@ #include "arrow/util/macros.h" #include "arrow/util/variant.h" #include "arrow/util/visibility.h" +#include "arrow/util/decimal_meta.h" #include "arrow/visitor.h" // IWYU pragma: keep namespace arrow { @@ -875,44 +876,37 @@ class ARROW_EXPORT DecimalType : public FixedSizeBinaryType { int32_t scale_; }; -/// \brief Concrete type class for 128-bit decimal data -class ARROW_EXPORT Decimal128Type : public DecimalType { +/// \brief Template type class for decimal data +template +class BaseDecimalType : public DecimalType { public: - static constexpr Type::type type_id = Type::DECIMAL128; - - static constexpr const char* type_name() { return "decimal"; } + static constexpr const char* type_name() { return DecimalMeta::name; } - /// Decimal128Type constructor that aborts on invalid input. - explicit Decimal128Type(int32_t precision, int32_t scale); + /// BaseDecimalType constructor that aborts on invalid input. + explicit BaseDecimalType(int32_t precision, int32_t scale); - /// Decimal128Type constructor that returns an error on invalid input. + /// BaseDecimalType constructor that returns an error on invalid input. static Result> Make(int32_t precision, int32_t scale); std::string ToString() const override; - std::string name() const override { return "decimal"; } + std::string name() const override { return DecimalMeta::name; } static constexpr int32_t kMinPrecision = 1; - static constexpr int32_t kMaxPrecision = 38; + static constexpr int32_t kMaxPrecision = DecimalMeta::max_precision; }; -/// \brief Concrete type class for 256-bit decimal data -class ARROW_EXPORT Decimal256Type : public DecimalType { - public: - static constexpr Type::type type_id = Type::DECIMAL256; - - static constexpr const char* type_name() { return "decimal256"; } - - /// Decimal256Type constructor that aborts on invalid input. - explicit Decimal256Type(int32_t precision, int32_t scale); - - /// Decimal256Type constructor that returns an error on invalid input. - static Result> Make(int32_t precision, int32_t scale); - - std::string ToString() const override; - std::string name() const override { return "decimal256"; } +/// \brief Concrete type class for decimal 128-bit data +class ARROW_EXPORT Decimal128Type : public BaseDecimalType<128> { +public: + static constexpr Type::type type_id = Type::DECIMAL128; + using BaseDecimalType<128>::BaseDecimalType; +}; - static constexpr int32_t kMinPrecision = 1; - static constexpr int32_t kMaxPrecision = 76; +/// \brief Concrete type class for decimal 256-bit data +class ARROW_EXPORT Decimal256Type : public BaseDecimalType<256> { +public: + static constexpr Type::type type_id = Type::DECIMAL256; + using BaseDecimalType<256>::BaseDecimalType; }; /// \brief Concrete type class for union data diff --git a/cpp/src/arrow/type_fwd.h b/cpp/src/arrow/type_fwd.h index e62a8ca0082..37ae9087ded 100644 --- a/cpp/src/arrow/type_fwd.h +++ b/cpp/src/arrow/type_fwd.h @@ -142,17 +142,20 @@ class StructArray; class StructBuilder; struct StructScalar; -class Decimal128; -class Decimal256; class DecimalType; -class Decimal128Type; -class Decimal256Type; -class Decimal128Array; -class Decimal256Array; -class Decimal128Builder; -class Decimal256Builder; -struct Decimal128Scalar; -struct Decimal256Scalar; + +#define DECIMAL_DECL(width) \ +class Decimal##width; \ +class Decimal##width##Type; \ +class Decimal##width##Array; \ +class Decimal##width##Builder; \ +struct Decimal##width##Scalar; + +DECIMAL_DECL(128) +DECIMAL_DECL(256) + +#undef DECIMAL_DECL + struct UnionMode { enum type { SPARSE, DENSE }; diff --git a/cpp/src/arrow/type_traits.h b/cpp/src/arrow/type_traits.h index 16f6a724d16..b7283060eea 100644 --- a/cpp/src/arrow/type_traits.h +++ b/cpp/src/arrow/type_traits.h @@ -281,22 +281,21 @@ struct TypeTraits { static inline std::shared_ptr type_singleton() { return float16(); } }; -template <> -struct TypeTraits { - using ArrayType = Decimal128Array; - using BuilderType = Decimal128Builder; - using ScalarType = Decimal128Scalar; - constexpr static bool is_parameter_free = false; -}; -template <> -struct TypeTraits { - using ArrayType = Decimal256Array; - using BuilderType = Decimal256Builder; - using ScalarType = Decimal256Scalar; - constexpr static bool is_parameter_free = false; +#define DECIMAL_TYPE_TRAITS_DEF(width) \ +template <> \ +struct TypeTraits { \ + using ArrayType = Decimal##width##Array; \ + using BuilderType = Decimal##width##Builder; \ + using ScalarType = Decimal##width##Scalar; \ + constexpr static bool is_parameter_free = false; \ }; +DECIMAL_TYPE_TRAITS_DEF(128) +DECIMAL_TYPE_TRAITS_DEF(256) + +#undef DECIMAL_TYPE_TRAITS_DEF + template <> struct TypeTraits { using ArrayType = BinaryArray; diff --git a/cpp/src/arrow/util/basic_decimal.cc b/cpp/src/arrow/util/basic_decimal.cc index ac85bd088ad..8895e6527bf 100644 --- a/cpp/src/arrow/util/basic_decimal.cc +++ b/cpp/src/arrow/util/basic_decimal.cc @@ -30,6 +30,7 @@ #include "arrow/util/bit_util.h" #include "arrow/util/int128_internal.h" #include "arrow/util/int_util_internal.h" +#include "arrow/util/decimal_meta.h" #include "arrow/util/logging.h" #include "arrow/util/macros.h" @@ -175,7 +176,7 @@ BasicDecimal128 BasicDecimal128::Abs(const BasicDecimal128& in) { bool BasicDecimal128::FitsInPrecision(int32_t precision) const { DCHECK_GT(precision, 0); - DCHECK_LE(precision, 38); + DCHECK_LE(precision, DecimalMeta<128>::max_precision); return BasicDecimal128::Abs(*this) < ScaleMultipliers[precision]; } @@ -699,7 +700,7 @@ DecimalStatus BasicDecimal128::Rescale(int32_t original_scale, int32_t new_scale const int32_t abs_delta_scale = std::abs(delta_scale); DCHECK_GE(abs_delta_scale, 1); - DCHECK_LE(abs_delta_scale, 38); + DCHECK_LE(abs_delta_scale, DecimalMeta<128>::max_precision); BasicDecimal128 result(*this); const bool rescale_would_cause_data_loss = @@ -716,7 +717,7 @@ DecimalStatus BasicDecimal128::Rescale(int32_t original_scale, int32_t new_scale void BasicDecimal128::GetWholeAndFraction(int scale, BasicDecimal128* whole, BasicDecimal128* fraction) const { DCHECK_GE(scale, 0); - DCHECK_LE(scale, 38); + DCHECK_LE(scale, DecimalMeta<128>::max_precision); BasicDecimal128 multiplier(ScaleMultipliers[scale]); auto s = Divide(multiplier, whole, fraction); @@ -725,7 +726,7 @@ void BasicDecimal128::GetWholeAndFraction(int scale, BasicDecimal128* whole, const BasicDecimal128& BasicDecimal128::GetScaleMultiplier(int32_t scale) { DCHECK_GE(scale, 0); - DCHECK_LE(scale, 38); + DCHECK_LE(scale, DecimalMeta<128>::max_precision); return ScaleMultipliers[scale]; } @@ -734,14 +735,14 @@ const BasicDecimal128& BasicDecimal128::GetMaxValue() { return kMaxValue; } BasicDecimal128 BasicDecimal128::IncreaseScaleBy(int32_t increase_by) const { DCHECK_GE(increase_by, 0); - DCHECK_LE(increase_by, 38); + DCHECK_LE(increase_by, DecimalMeta<128>::max_precision); return (*this) * ScaleMultipliers[increase_by]; } BasicDecimal128 BasicDecimal128::ReduceScaleBy(int32_t reduce_by, bool round) const { DCHECK_GE(reduce_by, 0); - DCHECK_LE(reduce_by, 38); + DCHECK_LE(reduce_by, DecimalMeta<128>::max_precision); if (reduce_by == 0) { return *this; @@ -788,7 +789,7 @@ BasicDecimal256::BasicDecimal256(const uint8_t* bytes) std::array({reinterpret_cast(bytes)[3], reinterpret_cast(bytes)[2], reinterpret_cast(bytes)[1], - reinterpret_cast(bytes)[0]})) { + reinterpret_cast(bytes)[0]})) {} #endif BasicDecimal256& BasicDecimal256::Negate() { diff --git a/cpp/src/arrow/util/decimal_meta.h b/cpp/src/arrow/util/decimal_meta.h new file mode 100644 index 00000000000..e5eb4d907a2 --- /dev/null +++ b/cpp/src/arrow/util/decimal_meta.h @@ -0,0 +1,37 @@ +// Licensed to the Apache Software Foundation (ASF) under one +// or more contributor license agreements. See the NOTICE file +// distributed with this work for additional information +// regarding copyright ownership. The ASF licenses this file +// to you under the Apache License, Version 2.0 (the +// "License"); you may not use this file except in compliance +// with the License. You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +#pragma once + +namespace arrow { + +template +struct DecimalMeta; + +template<> +struct DecimalMeta<128> { + static constexpr const char* name = "decimal"; + static constexpr int32_t max_precision = 38; +}; + +template<> +struct DecimalMeta<256> { + static constexpr const char* name = "decimal256"; + static constexpr int32_t max_precision = 76; +}; + +} // namespace arrow diff --git a/cpp/src/arrow/util/decimal_type_traits.h b/cpp/src/arrow/util/decimal_type_traits.h new file mode 100644 index 00000000000..fd8e9a5e1ff --- /dev/null +++ b/cpp/src/arrow/util/decimal_type_traits.h @@ -0,0 +1,41 @@ +// Licensed to the Apache Software Foundation (ASF) under one +// or more contributor license agreements. See the NOTICE file +// distributed with this work for additional information +// regarding copyright ownership. The ASF licenses this file +// to you under the Apache License, Version 2.0 (the +// "License"); you may not use this file except in compliance +// with the License. You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +#pragma once + +#include "arrow/type_fwd.h" + +namespace arrow { + +template +struct DecimalTypeTraits; + +#define DECIMAL_TYPE_TRAITS_DECL(width) \ +template<> \ +struct DecimalTypeTraits { \ + static constexpr Type::type Id = Type::DECIMAL##width; \ + using ArrayType = Decimal##width##Array; \ + using BuilderType = Decimal##width##Builder; \ + using ScalarType = Decimal##width##Scalar; \ + using TypeClass = Decimal##width##Type; \ + using ValueType = Decimal##width; \ +}; + +DECIMAL_TYPE_TRAITS_DECL(128) +DECIMAL_TYPE_TRAITS_DECL(256) + +} // namespace arrow