From 7bca0d82d7ee4f4f2ea4ffe559da7e48265fae2c Mon Sep 17 00:00:00 2001 From: arkady-e1ppa Date: Mon, 20 Nov 2023 13:44:15 +0300 Subject: YT-19593: Constexpr friendliness in strong typedef plus TAllocationId uses it now --- library/cpp/yt/misc/strong_typedef-inl.h | 45 ++++++++++++++++++++++++++++---- library/cpp/yt/misc/strong_typedef.h | 6 ++++- 2 files changed, 45 insertions(+), 6 deletions(-) diff --git a/library/cpp/yt/misc/strong_typedef-inl.h b/library/cpp/yt/misc/strong_typedef-inl.h index 0a1bd9427ae..59ff7cbce26 100644 --- a/library/cpp/yt/misc/strong_typedef-inl.h +++ b/library/cpp/yt/misc/strong_typedef-inl.h @@ -60,6 +60,32 @@ constexpr T&& TStrongTypedef::Underlying() && return std::move(Underlying_); } +template +constexpr bool TStrongTypedef::operator==(const TStrongTypedef& rhs) const +noexcept(std::same_as || noexcept(Underlying_ == rhs.Underlying_)) +{ + //! NB: We add a constexpr branch to keep constexprness of the function + //! without making extra specializations explicitly. + if constexpr (std::same_as) { + return true; + } + + return Underlying_ == rhs.Underlying_; +} + +template +constexpr auto TStrongTypedef::operator<=>(const TStrongTypedef& rhs) const +noexcept(std::same_as || noexcept(Underlying_ <=> rhs.Underlying_)) +{ + //! NB: We add a constexpr branch to keep constexprness of the function + //! without making extra specializations explicitly. + if constexpr (std::same_as) { + return std::strong_ordering::equal; + } + + return Underlying_ <=> rhs.Underlying_; +} + //////////////////////////////////////////////////////////////////////////////// template @@ -117,13 +143,22 @@ struct hash> //////////////////////////////////////////////////////////////////////////////// -template -struct THash; - template struct THash> - : public std::hash> -{ }; +{ + size_t operator()(const NYT::TStrongTypedef& value) const + { + static constexpr bool IsTHashable = requires (T val) { + { THash()(val) } -> std::same_as; + }; + + if constexpr (IsTHashable) { + return THash()(value.Underlying()); + } else { + return std::hash()(value.Underlying()); + } + } +}; //////////////////////////////////////////////////////////////////////////////// diff --git a/library/cpp/yt/misc/strong_typedef.h b/library/cpp/yt/misc/strong_typedef.h index 545029db8d4..d42f9e1f74b 100644 --- a/library/cpp/yt/misc/strong_typedef.h +++ b/library/cpp/yt/misc/strong_typedef.h @@ -30,7 +30,11 @@ public: constexpr explicit operator const T&() const; constexpr explicit operator T&(); - constexpr auto operator<=>(const TStrongTypedef& rhs) const = default; + constexpr bool operator==(const TStrongTypedef& rhs) const + noexcept(std::same_as || noexcept(Underlying_ == rhs.Underlying_)); + + constexpr auto operator<=>(const TStrongTypedef& rhs) const + noexcept(std::same_as || noexcept(Underlying_ <=> rhs.Underlying_)); constexpr T& Underlying() &; constexpr const T& Underlying() const &; -- cgit v1.3