// Copyright (c) 2022, Cppreference.com // // Distributed under the terms of the Copyright/CC-BY-SA License. // // The full license can be found at the address // https://en.cppreference.com/w/Cppreference:Copyright/CC-BY-SA /** * Backport of C++20 ``std::cmp_*`` functions for signed comparison. */ #ifndef MAMBA_CORE_UTIL_COMPARE_HPP #define MAMBA_CORE_UTIL_COMPARE_HPP #include #if __cplusplus >= 202002L #define MAMBA_UTIL_COMPARE_DEPRECATED [[deprecated("Use C++20 functions with the same name")]] #else #define MAMBA_UTIL_COMPARE_DEPRECATED #endif namespace mamba::util { template MAMBA_UTIL_COMPARE_DEPRECATED constexpr bool cmp_equal(T t, U u) noexcept { using UT = std::make_unsigned_t; using UU = std::make_unsigned_t; if constexpr (std::is_signed_v == std::is_signed_v) { return t == u; } else if constexpr (std::is_signed_v) { return t < 0 ? false : UT(t) == u; } else { return u < 0 ? false : t == UU(u); } } template MAMBA_UTIL_COMPARE_DEPRECATED constexpr bool cmp_not_equal(T t, U u) noexcept { return !cmp_equal(t, u); } template MAMBA_UTIL_COMPARE_DEPRECATED constexpr bool cmp_less(T t, U u) noexcept { using UT = std::make_unsigned_t; using UU = std::make_unsigned_t; if constexpr (std::is_signed_v == std::is_signed_v) { return t < u; } else if constexpr (std::is_signed_v) { return t < 0 ? true : UT(t) < u; } else { return u < 0 ? false : t < UU(u); } } template MAMBA_UTIL_COMPARE_DEPRECATED constexpr bool cmp_greater(T t, U u) noexcept { return cmp_less(u, t); } template MAMBA_UTIL_COMPARE_DEPRECATED constexpr bool cmp_less_equal(T t, U u) noexcept { return !cmp_greater(t, u); } template MAMBA_UTIL_COMPARE_DEPRECATED constexpr bool cmp_greater_equal(T t, U u) noexcept { return !cmp_less(t, u); } } #endif