Question: How would you write a template function that takes a variable number of homogeneous non-POD function arguments in C++11?

For example suppose we wanted to write a min function for any type that defines the less than "operator<" as follows:

```
// pseduo-code...

template<class T...>
T min(T x1, T x2, ..., T xn)
{
    T lowest = x1;

    for (T x : {x2,...,xn})
       if (x < lowest)
           lowest = x;

    return lowest;
}

```

The above is illegal C++11, how would you write it legally?

Answer: 
This is a little convoluted but that's what you get if you want
heterogeneous arguments:

```
#include <iostream>
#include <type_traits>

template<typename F, typename T, typename Arg>
auto fold(F f, T&& t, Arg&& a) 
  -> decltype(f(std::forward<T>(t), std::forward<Arg>(a)))
{ return f(std::forward<T>(t), std::forward<Arg>(a)); }

template<typename F, typename T, typename Head, typename... Args>
auto fold(F f, T&& init, Head&& h, Args&&... args) 
  -> decltype(f(std::forward<T>(init), std::forward<Head>(h)))
{ 
  return fold(f, f(std::forward<T>(init), std::forward<Head>(h)), 
              std::forward<Args>(args)...); 
}

// polymorphic less
struct p_less {
  template<typename T, typename U>
  typename std::common_type<T, U>::type 
  operator()(T&& t, U&& u) const {
    return t < u ? t : u;
  }
};

// heterogeneous arguments possible
template<typename Head, typename... Args>
auto min(Head&& h, Args&&... args) -> typename std::common_type<Head, Args...>::type
{
  return fold(p_less(), std::forward<Head>(h), 
              std::forward<Args>(args)...);
}

// only considers homogeneous arguments
template<typename Head, typename... Args>
auto hmin(Head&& h, Args&&... args) -> Head
{
  return fold([](Head x, Head y) -> Head { return x < y ? x : y; }, 
              std::forward<Head>(h), std::forward<Args>(args)...);
}

int main()
{

  double x = 2.0, x2 = 3.0;
  int y = 2;

  auto d1 = min(3, 4.0, 2.f, 6UL);
  auto d2 = min(x, y);
  auto d3 = hmin(x, x2);
  auto b = hmin(3, 2, 7, 10);

  std::cout << d1 << std::endl;
  std::cout << d2 << std::endl;
  std::cout << d3 << std::endl;

  std::cout << b << std::endl;
  return 0;
}

```

The first version is a lot more interesting however. `common_type`
looks for the type that all arguments can be coerced to. This is
necessary because a function with heterogeneous arguments returning
either of them needs to find this type. However, this could be
circumvented using `boost::variant` but for built-in types this is
rather pointless as they have to be coerced to be compared anyway.
Another possibility:

```
template <typename T, typename... T2>
T min(T x1, T2... rest);

template <typename T>
T min(T x)
{
  return x;
}

template <typename T, typename... T2>
T min(T x1, T2... rest)
{
  return std::min (x1, min (rest...));
}

```

While this doesn't seem to enforce homogenity, calling with e.g. `int` and `long` gives compilation errors. Unfortunately, I'm not that good at standardese to say if it is supposed to be so.