【问题标题】:Create template pack from set of traits从一组特征创建模板包
【发布时间】:2021-02-06 19:57:03
【问题描述】:

是否可以(如果可以,如何)从一组索引类型特征生成模板包,以便它们可以用于实例化变体或元组?

#include <variant>

template<int n>
struct IntToType;

template<>
struct IntToType<0>
{
    using type = int;
    static constexpr char const* name = "int";
//  Other compile-time metadata
};

template<>
struct IntToType<1>
{
    using type = double;
    static constexpr char const* name = "double";
//  Other compile-time metadata
};

using MyVariant = std::variant<IntToType<???>::type...>;  // something with make_integer_sequence and fold expression?

或者是否有必要使用变体作为输入:

#include <variant>

using MyVariant = std::variant<int, double>;

template<int n>
struct IntToTypeBase
{
    using type = std::variant_alternative_t<n, MyVariant>;
};

template<int >
struct IntToType;

template<>
struct IntToType<0>:IntToTypeBase<0>
{
    static constexpr char const* name = "int";
//  Other compile-time metadata
};

template<>
struct IntToType<1>:IntToTypeBase<1>
{
    static constexpr char const* name = "double";
//  Other compile-time metadata
};

甚至推出你自己的variant,它接受一组特征而不是简单的类型列表:

template<class IntegerType, template<auto> class Traits, size_t LastIndex>
class Variant;

【问题讨论】:

    标签: c++ variadic-templates fold-expression


    【解决方案1】:

    你可以这样做:

    #include <variant>
    
    template<int n>
    struct IntToType;
    
    template<>
    struct IntToType<0>
    {
        using type = int;
        static constexpr char const* name = "int";
    //  Other compile-time metadata
    };
    
    template<>
    struct IntToType<1>
    {
        using type = double;
        static constexpr char const* name = "double";
    //  Other compile-time metadata
    };
    
    // replace NUMBER_OF_TYPES
    template <typename T=std::make_index_sequence<NUMBER_OF_TYPES> >
    struct make_my_variant;
    
    template <size_t... indices>
    struct make_my_variant<std::index_sequence<indices...> > {
        using type = std::variant<typename IntToType<indices>::type...>;
    };
    
    using MyVariant = typename std::make_my_variant<>::type;
    

    注意要查找类型名作为字符串文字,您可以使用typeid(TYPE).name()。如果您愿意,您可能需要解除此名称;您可以使用特定于编译器的 demangler 函数(我认为 MSVC 不会破坏类型名称,但在 GCC 上,您会在 &lt;cxxabi.h&gt; 标头中使用 abi::__cxa_demangle。)

    【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-10-03
    • 1970-01-01
    • 2018-02-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-06-03
    相关资源
    最近更新 更多