Sample implementation
template<typename T1, typename T2> struct simple_pair { simple_pair (T1 const& v1, T2 const& v2) // (1) : first (v1) , second (v2) { } template<class U, class V> simple_pair (U&& v1, V&& v2) // (2) : first (std::forward<U> (v1)) , second (std::forward<V> (v2)) { } T1 first; T2 second; };
Even though it might seem superfluous to provide both overload (1) and (2) there are cases where the second isn't usable, and the first one is not only preferred but actually required.
Consider that we'd like to construct some or both of our values while passing them to the constructor of simple_pair, without the first overload we would explicitly have to specify at least one of the types a second time.
T val; simple_pair<T, U> p1 { {}, {} }; // only (1) is applicable simple_pair<T, U> p2 { val, {} }; // only (1) is applicable simple_pair<T, U> p3 { T {}, U {} }; // can use (1) and (2), but this require a lot of typing
Alternative implementation
If we instead had an implemenation using something as the below we could get around the "superfluous" overloads since the compiler would then know what type we'd like to construct in cases where such information is required.
template<typename T1, typename T2> struct simple_pair { template<class U = T1, class V = T2> simple_pair (U&& v1, V&& v2) : first (std::forward<U> (v1)) , second (std::forward<V> (v2)) { } T1 first; T2 second; };
T val; simple_pair<T, U> p1 { {}, {} }; // legal simple_pair<T, U> p2 { val, {} }; // legal simple_pair<T, U> p3 { T {}, U {} }; // legal
Why isn't std::pair stated to be implemented using the alternative implementation?
We can only guess, but presumably it's because of backward compatibility and the fact that specifying it the way it currently stands ease1 implementation for library implementors.
By having two separate overload one can easily disable the template<class U, class V> simple_pair (U&&, V&&) overload by conditionally adding it using macros (to see if we are using c++11 (or later)), instead of conditionally opting it out and adding another one.
Further potential reasons
Removing something from the standard is always a delicate thing to do.. following the better safe than sorry idiom; "if it doesn't hurt, leave it in." - @PlasmaHH
Everyone knows that the more lines of code you write, the better programmer you are.. and the better programmer you are; the more you get payed.
1. surely not by much, but heck.. it doesn't hurt being a bit pedantic.. ;-)
pairto be used with both types.