Question

So I have a simple problem, that turns out to be a lot harder to solve than I anticipated.

Code:

template <typename R, typename... Args>
void ApplyString(R(*func)(Args...), std::string args)
{
    auto argtuple = std::make_tuple(GetToken<Args>(args)...);
    typename GetIndexTuple<Args...>::type indices;
    ApplyTuple(func, argtuple, indices);
}

Goal:

The goal of the code is to tokenize each function argument from a string. What I'm doing is applying the tokenizing function as I'm expanding the parameter pack (Args...) into a tuple. I then use that function to call ApplyTuple which does what it says. And it does work... kinda...

Problem:

The problem is that in the make_tuple sequence, the last function is called first. For example, lets say I have a simple output function:

void Output(int a, int b, int c)
{
    std::cout << a << "," << b << "," << c << "\n";
}

Then I use it like so:

ApplyString(Output, "10 7 5 ");

The expected output would be: 10,7,5. However the actual output is: 5,7,10. I was wondering if anybody knows of a way to help me work around this. From what I understand, it seems that the function call order is the opposite from the parameter pack expansion order. Am I understanding it correctly?

Thanks in advance!

Was it helpful?

Solution

So I figured something out, and while its not the most pretty it does work. I made a function to build a tuple of the specified type out of a string, then I just used that in place of make_tuple.

Code:

template <typename Head, typename... Tail>
std::tuple<Head, Tail...> StringToTuple(std::tuple<Head, Tail...>, std::string& args)
{
    auto head = std::make_tuple(GetToken<Head>(args));
    return std::tuple_cat(head, StringToTuple(std::tuple<Tail...>(), args));
}
std::tuple<> StringToTuple(std::tuple<>, std::string& args)
{
    return std::tuple<>();
}

template <typename R, typename... Args>
R ApplyString(std::function<R(Args...)> func, std::string args)
{
    std::tuple<Args...> argtuple = StringToTuple(std::tuple<Args...>(), args);
    return ApplyTuple(func, argtuple);
}

It does work now but if anyone has a better solution, please post it. Cheers!

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top