Converting Variadic template pack into std::initializer_list

后端 未结 3 1818
盖世英雄少女心
盖世英雄少女心 2021-02-03 11:52

Assume that there is a function which accepts several strings:

void fun (const std::initializer_list& strings) {
  for(auto s : strings)
          


        
3条回答
  •  春和景丽
    2021-02-03 12:22

    As for the second question, just do it this way:

    template
    void foo () {
      fun({Args::value...});
    }
    

    The mechanism is pretty intuitive: you create an initalizer list that contains the expanded Args::value pattern, thus resolving (in your case) to { A::value, B::value, C::value, D::value }.

    Here is a complete program:

    #include 
    #include 
    
    void fun (const std::initializer_list& strings) {
        for(auto s : strings)
        {
            std::cout << s << " ";
        }
    }
    
    template
    void foo () {
      fun({Args::value...});
    }
    
    struct A { static std::string value; };
    struct B { static std::string value; };
    struct C { static std::string value; };
    struct D { static std::string value; };
    
    std::string A::value = "Hello";
    std::string B::value = "World";
    std::string C::value = "of";
    std::string D::value = "Variadic Templates";
    
    int main()
    {
        foo(); // where A, B, C, D are classes
    }
    

    And here is a live example.

    As for the static assertion, you may write a type trait that determines whether a certain type has a member variable value:

    template
    struct has_value : std::false_type { };
    
    template
    struct has_value().value), void>::value,
            bool
            >::type
        > : std::true_type
    {
        typedef decltype(std::declval().value) type;
    };
    

    Then, you could use it this way:

    template
    struct check_has_value
    {
        static_assert(has_value::value, "!");
    };
    
    template
    void foo () {
        auto l = { (check_has_value(), 0)... };
        fun({Args::value...});
    }
    

    Here is a live example of a successful check (all classes has a value data member). Here is a live example of an unsuccessful check (class D's data member is called values)

提交回复
热议问题