C+ 17替代C+ 20;关键词

发布于 2025-02-11 06:21:38 字数 886 浏览 1 评论 0原文

C ++ 20引入了许多改进,例如需要概念 s,约束,模块等等 - 您在C ++中真正错过的功能17 。

如何在C ++ 17中实现具有条件构造函数的方案,这看起来像以下C ++ 20示例(使用需要)?

template <typename T> concept has_type = requires { typename T::type; };

template <typename T>
class someClass {
public:
    using data_t = typename std::conditional_t<has_type<T>, T, std::type_identity<T> >::type;

    constexpr someClass(T const& _a, T const& _b) requires std::is_arithmetic_v<T> : a{_a}, b{_b} {}
    constexpr someClass(data_t const& _a, data_t const& _b,) requires has_type<T> : a{_a}, b{_b} {}

private:
    const data_t a, b;
};

必须在t的情况下使用一个构造函数(intfloatdouble,。 ..)。 另一个构造函数需要捕获t是具有嵌套type别名的类/结构的情况(例如代码>)。

C++20 introduced many improvements like requires, concepts, constraints, modules and much more - functionality you really miss in C++17.

How can a scenario having conditional constructors be implemented in C++17, that could look like the following C++20 example (using requires)?

template <typename T> concept has_type = requires { typename T::type; };

template <typename T>
class someClass {
public:
    using data_t = typename std::conditional_t<has_type<T>, T, std::type_identity<T> >::type;

    constexpr someClass(T const& _a, T const& _b) requires std::is_arithmetic_v<T> : a{_a}, b{_b} {}
    constexpr someClass(data_t const& _a, data_t const& _b,) requires has_type<T> : a{_a}, b{_b} {}

private:
    const data_t a, b;
};

One constructor has to be used in case of T is an arithmetic type (int, float, double, ...).
Another constructor needs to catch the case of T being a class/struct having a nested type alias (e.g. struct x { using type=float; };).

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

庆幸我还是我 2025-02-18 06:21:38

使用 sfinae

template <typename, typename = std::void_t<>>
struct HasTypeT : std::false_type {};

template <typename T>
struct HasTypeT<T, std::void_t<typename T::type>> : std::true_type {};


template <typename T>
struct type_identity {
    using type = T;
};

template <typename T>
class someClass {
public:
    using data_t = typename std::conditional_t<HasTypeT<T>::value, T, type_identity<T> >::type;

    template <typename U = T, typename = std::enable_if_t<std::is_arithmetic_v<U>>>
    constexpr someClass(T const& _a, T const& _b) : a{_a}, b{_b} {}

    template <typename U = T, typename = std::enable_if_t<HasTypeT<U>::value>>
    constexpr someClass(typename U::type const& _a, typename U::type const& _b) : a{_a}, b{_b} {}

private:
    const data_t a, b;
};

//godbolt.org/z/gyejharsa“ rel =“ nofollow noreferrer”> demo

Using SFINAE

template <typename, typename = std::void_t<>>
struct HasTypeT : std::false_type {};

template <typename T>
struct HasTypeT<T, std::void_t<typename T::type>> : std::true_type {};


template <typename T>
struct type_identity {
    using type = T;
};

template <typename T>
class someClass {
public:
    using data_t = typename std::conditional_t<HasTypeT<T>::value, T, type_identity<T> >::type;

    template <typename U = T, typename = std::enable_if_t<std::is_arithmetic_v<U>>>
    constexpr someClass(T const& _a, T const& _b) : a{_a}, b{_b} {}

    template <typename U = T, typename = std::enable_if_t<HasTypeT<U>::value>>
    constexpr someClass(typename U::type const& _a, typename U::type const& _b) : a{_a}, b{_b} {}

private:
    const data_t a, b;
};

Demo

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文