How can I implement a generic min?

c++, templates

Solution

That's because non-`const` lvalue references (`T&`) cannot bind to rvalues (`3` and `4` are rvalues, which intuitively means that they do not have an object identity).

Try using lvalue references to `const` instead, which can bind to rvalues (after all, the `min()` function is not supposed to alter the state of its arguments).

Besides, do not forget the `template<typename T>` part if you are writing a function template:

template<typename T> // <== Don't forget this, if you are writing a template
T min(T const& a, T const& b)
//      ^^^^^       ^^^^^
{
    return (a < b) ? a : b;
}

For instance, consider this small program:

#include <iostream>

template<typename T> // <== Don't forget this, if you are writing a template
T min(T const& a, T const& b)
//      ^^^^^       ^^^^^
{
    return (a < b) ? a : b;
}

int main()
{
    int x = 42;
    int y = 1729;

    std::cout << min(x, y) << std::endl; // Passing lvalues, that would be OK also
                                         // with your original code.

    std::cout << min(42, 1729) << std::endl; // Passing rvalues, this would not be OK
                                             // with your original code (non-const
                                             // lvalue references cannot bind to rvalues)
}

Here is a live example.

UPDATE:

The above solution only allows passing values of the same type to `min()`, otherwise the compiler won't be able to perform type deduction (if the first and second argument have different types, what should `T` be?):

min(3.14, 42); // Huh? What is `T` here, `double` or `int`?

To force the compiler to use a specific type for `T`, you can specify the template argument explicitly:

min<double>(3.14, 42);

However, this is not a very elegant choice (the user has to type the correct template argument manually every time). Rather, you could let your function template accept two template type parameters instead of one:

#include <type_traits>

template<typename T, typename U>
typename std::common_type<T, U>::type min(T const& a, U const& b)
{
    return (a < b) ? a : b;
}

And use the `std::common_type<>` type trait (available since C++11) to figure out the right type to be used as the return type.

Once again, here is a live example.

Problem

When I write ``` T min(T& a,T& b) {return a<b?a:b;} ``` and call `min(3,4)`, it will yield a error. How can I implement a generic min?

Original source