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 &lt;functional&gt;

template &lt;class Output, class... Inputs&gt;
std::function&lt;typename Output::result_type(typename Inputs::result_type...)&gt;
make_function(const Output&amp; output, Inputs&amp;... inputs) {
  return[&amp;](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.
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 &lt;class Output, class... Inputs&gt;
auto make_function(const Output&amp; output, Inputs&amp;... inputs) {
  return [&amp;](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).