Search code examples
c++boostc++14boost-hana

C++: Expand array elements as parameter of a function using boost::hana


I discovered two months ago boost::hana. Seems very powerfull so I decided to take a look. From the documentation I saw this examples:

std::string s;
hana::int_c<10>.times([&]{ s += "x"; });

that is equivalent to:

s += "x"; s += "x"; ... s += "x"; // 10 times

I'd like to know if it is possible (and if yes how) to write smthg like:

std::string s;
std::array<int, 10> xs = {1, 3, 5, ...};
hana::int_c<10>.times([&](int i){ s += std::to_string(xs[i]) + ","; });

a sort of "unpacking" at compile time, or even:

myfunction( hana::unpack<...>( xs ) );

Solution

  • Your question seems twofold. First, the title of your question asks whether it is possible to expand the elements of an array as the parameters of a function. It is indeed possible, since std::array is Foldable. It suffices to use hana::unpack:

    #include <boost/hana/ext/std/array.hpp>
    #include <boost/hana/unpack.hpp>
    #include <array>
    namespace hana = boost::hana;
    
    
    struct myfunction {
        template <typename ...T>
        void operator()(T ...i) const {
            // whatever
        }
    };
    
    int main() {
        std::array<int, 10> xs = {{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}};
        hana::unpack(xs, myfunction{});
    }
    

    Secondly, you ask whether it is possible to do something like

    std::string s;
    std::array<int, 10> xs = {1, 3, 5, ...};
    hana::int_c<10>.times([&](int i){ s += std::to_string(xs[i]) + ","; });
    

    The answer to this is to use hana::int_c<10>.times.with_index:

    hana::int_c<10>.times.with_index([&](int i) { s += std::to_string(xs[i]) + ","; });    
    

    Equivalently, you could also use hana::for_each:

    hana::for_each(xs, [&](int x) { s += std::to_string(x) + ","; });