# Most elegant variadic functor

Question

Suppose we have two sorts of classes

• an input class Input
• defines a type result_type
• defines set(result_type)
• an output class Output
• defines a type result_type
• defines result_type get() const
• has a number of Input classes as member variables, on which its output depends

Given an output class and several input classes (arbitrary number), consider the following procedure:

• loop over each input class and call set() with an appropriate value (defined beforehand)
• call the get() on the ouput class and collect the result.

This procedure can be seen as a call to a function taking the input's values as arguments an returning the output value.

Write the functor that constructs such a variadic function in the general case.

Constraints are: C++ (most likely C++11), arbitrary number of input classes of possibly different Input::result_types. Note that Input::result_type is not necessarily related to Output::result_type. Aim should first be efficiency, but there's a big bonus if the code is elegant and readable.

Details: For those who wonder how Output is related to Input, one could imagine that Input has a result_type get() const method as well, which returns whatever you provided via set(). Output then has a constructor that takes various Inputs, and stores them (or their reference) as member variables. Output::get() then does some math by using the return values of its input's get() methods, and returns some result of type Output::result_type.

Proposed solution

#include <functional>

template <class Output, class... Inputs>
std::function<typename Output::result_type(typename Inputs::result_type...)>
make_function(const Output& output, Inputs&... inputs) {
return[&](typename Inputs::result_type... input_vals) {
int dummy[]{0, (inputs.set(input_vals),0)...};
return output.get();
};
}


The int dummy[] line is due to @ecatmur's answer.

• Just as a question, how are the arbitrary number of Inputs stored in Output? – Yuushi Jan 22 '14 at 1:46
• there are multiple classes that have a fixed number of inputs, and each store them in a similar way (see details section). – yannick Jan 22 '14 at 9:22
• Ok. I was asking because if they are all the same type, then I think there is a more elegant solution. Having them be heterogeneous types makes it more difficult, however. I might think about it a bit more, but I will say that if you're looking for efficiency, I'd try and avoid std::function if possible. – Yuushi Jan 24 '14 at 0:01
• by what would you replace std::function then? – yannick Jan 28 '14 at 10:55
• In this case, you likely don't have a choice without changing the design significantly. In C++14, this may change with generic lambdas. That being said, having thought about it, I don't think this can really be improved upon. – Yuushi Jan 29 '14 at 1:47

Looks to me as if you've already got the most elegant solution in mind.

In C++14 you'd remove the dependency on std::function and simply return a naked lambda, like this:

template <class Output, class... Inputs>
auto make_function(const Output& output, Inputs&... inputs) {
return [&](typename Inputs::result_type... input_vals) {
int dummy[] { 0, ((void)inputs.set(input_vals),0)... };
return output.get();
};
}


but in C++11 you can't make a function-that-returns-a-naked-lambda without a ton of boilerplate — if it's even possible at all.

Also, a nitpick, with props to @stephan-t-lavavej's talk at CppCon 2014. You wrote

(inputs.set(input_vals),0)...


but what you should have written was

((void)inputs.set(input_vals),0)...


to avoid accidentally calling MaliciousUserCode::operator,(int).