lambda traits inconsistency across C++0x compilers - c++

I observed some inconsistency between two compilers (g++ 4.5, VS2010 RC) in the way they match lambdas with partial specializations of class templates. I was trying to implement something like boost::function_types for lambdas to extract type traits. Check this for more details.
In g++ 4.5, the type of the operator() of a lambda appears to be like that of a free standing function (R (*)(...)) whereas in VS2010 RC, it appears to be like that of a member function (R (C::*)(...)). So the question is are compiler writers free to interpret any way they want? If not, which compiler is correct? See the details below.
template <typename T>
struct function_traits
: function_traits<decltype(&T::operator())>
{
// This generic template is instantiated on both the compilers as expected.
};
template <typename R, typename C>
struct function_traits<R (C::*)() const> { // inherits from this one on VS2010 RC
typedef R result_type;
};
template <typename R>
struct function_traits<R (*)()> { // inherits from this one on g++ 4.5
typedef R result_type;
};
int main(void) {
auto lambda = []{};
function_traits<decltype(lambda)>::result_type *r; // void *
}
This program compiles on both g++ 4.5 and VS2010 but the function_traits that are instantiated are different as noted in the code.

I believe that GCC is noncompliant. N3092 §5.1.2/5 says
The closure type for a
lambda-expression has a public inline
function call operator (13.5.4) whose
param- eters and return type are
described by the lambda-expression’s
parameter-declaration-clause and
trailing- return-type respectively.
This function call operator is
declared const (9.3.1) if and only if
the lambda- expression’s
parameter-declaration-clause is not
followed by mutable.
So while many things about the closure object's type are implementation-defined, the function itself must be a member to be public and must be a nonstatic member to be const.
EDIT: This program indicates that operator() is a member function on GCC 4.6, which is essentially the same as 4.5.
#include <iostream>
#include <typeinfo>
using namespace std;
template< class ... > struct print_types {};
template<> struct print_types<> {
friend ostream &operator<< ( ostream &lhs, print_types const &rhs ) {
return lhs;
}
};
template< class H, class ... T > struct print_types<H, T...> {
friend ostream &operator<< ( ostream &lhs, print_types const &rhs ) {
lhs << typeid(H).name() << " " << print_types<T...>();
return lhs;
}
};
template< class T >
struct spectfun {
friend ostream &operator<< ( ostream &lhs, spectfun const &rhs ) {
lhs << "unknown";
return lhs;
}
};
template< class R, class ... A >
struct spectfun< R (*)( A ... ) > {
friend ostream &operator<< ( ostream &lhs, spectfun const &rhs ) {
lhs << "returns " << print_types<R>()
<< " takes " << print_types<A ...>();
return lhs;
}
};
template< class C, class R, class ... A >
struct spectfun< R (C::*)( A ... ) > {
friend ostream &operator<< ( ostream &lhs, spectfun const &rhs ) {
lhs << "member of " << print_types<C>() << ", " << spectfun<R (*)(A...)>();
return lhs;
}
};
template< class T >
struct getcall {
typedef decltype(&T::operator()) type;
};
int main() {
int counter = 0;
auto count = [=]( int ) mutable { return ++ counter; };
cerr << spectfun< getcall<decltype(count)>::type >() << endl;
}
output:
member of Z4mainEUlvE_, returns i takes i
EDIT: It looks like the only problem is that pointers to certain closure call operators fail to match ptmf template patterns. The workaround is to declare the lambda expression mutable. This is meaningless if there is no capture and only (aside from fixing the problem) seems to change the const-ness of the call operator.
template< class T >
struct getcall {
typedef decltype(&T::operator()) type;
static type const value;
};
template< class T >
typename getcall<T>::type const getcall<T>::value = &T::operator();
int main() {
auto id = []( int x ) mutable { return x; };
int (*idp)( int ) = id;
typedef decltype(id) idt;
int (idt::*idptmf)( int ) /* const */ = getcall< decltype(id) >::value;
cerr << spectfun< decltype(idp) >() << endl;
cerr << spectfun< decltype(idptmf) >() << endl;
cerr << spectfun< getcall<decltype(id)>::type >() << endl;
output:
returns i takes i
member of Z4mainEUliE0_ , returns i takes i
member of Z4mainEUliE0_ , returns i takes i
Without the mutable and with the const, spectfun does not print signatures for either of the last two queries.

Read n3043. Lambdas are now convertible to function pointers provided they don't have any state. I believe (...but do not know) GCC initially implemented this behavior accidentally, "fixed it", now will be re-adding it to 4.5 or 4.6. VC10 implemented lambdas correctly as initially designed, but not conforming to the latest working papers with n3043.

I think gcc developers has a good reason for this behaivor. Remember, a static function do not have a "this" pointer, and when it is being actually called, the caller do not required to pass the "this" pointer. So this is a small performance optimisation when it is actually nothing contained in the closure object. And you can see the G++ developer leave you a way to workaround by declaring the lambda expression as "mutable" (remember you actually do not have anything to mutate).

Related

Using SFINAE to detect if overloaded free-standing function exists at compile-time

Here is my unsuccessful attempt at detecting whether a free-standing function void set( T& , void (T::*Func)( const char* ) , const char* str ) exists for any class/struct T, in C++98/03.
#include <iostream>
#include <typeinfo>
struct Foo;
struct Bar;
struct Fuu;
void set( Foo& , void (Foo::*Func)( const char* ) , const char* str )
{
}
void set( Bar& , void (Bar::*Func)( const char* ) , const char* str )
{
}
template <typename T>
class setter_is_implemented
{
public:
typedef void (*SetterFunction)( T& , void (T::*)( const char* ) , const char* );
typedef char one;
typedef long two;
template <typename C> static one test( C c, SetterFunction = c ) ;
template <typename C> static two test(...);
public:
enum { value = sizeof( test<T>(&set)) == sizeof(one) };
};
int main()
{
std::cout << setter_is_implemented<Foo>::value << std::endl;
std::cout << setter_is_implemented<Bar>::value << std::endl;
std::cout << setter_is_implemented<Fuu>::value << std::endl;
}
GCC error message
Test.cpp:24:66: error: ‘c’ was not declared in this scope
template <typename C> static one test( C c, SetterFunction = c ) ;
^
Test.cpp: In instantiation of ‘class setter_is_implemented<Foo>’:
Test.cpp:33:44: required from here
Test.cpp:28:35: error: address of overloaded function with no contextual type information
enum { value = sizeof( test<T>(&set)) == sizeof(one) };
^
Test.cpp: In instantiation of ‘class setter_is_implemented<Bar>’:
Test.cpp:34:44: required from here
Test.cpp:28:35: error: address of overloaded function with no contextual type information
Test.cpp: In instantiation of ‘class setter_is_implemented<Fuu>’:
Test.cpp:35:44: required from here
Test.cpp:28:35: error: address of overloaded function with no contextual type information
AFAIK, taking the address of an overloaded function happens before overload resolution, so SFINAE cannot work in that way. This is also harder because your function returns void (otherwise, one would just check the size of the result ). My C++03 metaprogramming is rusty, but this should work (live on coliru):
namespace setter_is_implemented_detail {
struct dummy1 { char c[2]; };
typedef char dummy2;
dummy2 operator,(dummy1, dummy1);
template<typename T> dummy1 set(T const&,...);
template <typename T>
struct impl
{
typedef void (T::*FT)( const char* );
static T& x;
enum { value = sizeof( set(x,static_cast<FT>(0),static_cast<const char*>(0)), dummy1() ) != sizeof(dummy2) };
};
}
template <typename T>
struct setter_is_implemented: setter_is_implemented_detail::impl<T>{};
note a few things:
set() needs to be found by ADL here (not a big deal, as far as I can tell from your problem description)(*)
the comma operator trick(**) is needed due to the void return type; in gcc, you can take the sizeof(void), so the code can be simplified there
this won't work for non object types (due to the static T&). It can be made to work though, if you need so...
(*) Note that this cannot work for every possible set() overload; this is true for any sfinae, even in c++17, set() must always be sfinae-friendly in order to work.
If you need to match sfinae-friendly set() overloads exactly, it's still possible to do it, but it's more complex; I'd do it in two phases: first you use the above code to find possible candidates, then you check the function pointer conversion, somewhat like you do in your original code ..
(**) This trick works because if set() has void return type (and hence exists) the comma is always interpreted as the built-in comma operator (see c++03[3.9.1/9]: "An expression of type void shall be used only as an expression statement (6.2), as an operand of a comma expression[...]") resulting in the right-most expression. Otherwise, the dummy set and comma operator are used.

Template operator< not called

The following code implements template class Data whose purpose is to compare its member object. The intent is that if the member object is of the same type, that object's operator< is used for the comparison, and if the member objects are of different types, std::string's operator< is used on a stringification of the member objects.
#include <iostream>
#include <sstream>
template <typename T>
class Data
{
public:
Data( const T& t ) : m_data( t ) {}
template <typename U> bool operator<( const Data<U>& cu )
{
std::cout << __PRETTY_FUNCTION__ << std::endl;
return ( static_cast<std::ostringstream&>(( std::ostringstream().flush() << m_data )).str() <
static_cast<std::ostringstream&>(( std::ostringstream().flush() << cu.m_data )).str() );
}
#if 1 // Change this to "#if 0" and code doesn't work anymore.
bool operator<( const Data<T>& ct )
{
std::cout << __PRETTY_FUNCTION__ << std::endl;
return ( m_data < ct.m_data );
}
#endif
private:
T m_data;
template< typename U> friend class Data;
friend bool operator< <T> ( const Data<T>&, const Data<T>& );
};
template<typename T>
bool operator<( const Data<T>& a, const Data<T>& b )
{
std::cout << __PRETTY_FUNCTION__ << std::endl;
return ( a.m_data < b.m_data );
}
int main( int argc, char* argv[] )
{
Data<int> a(10);
Data<std::string> b("2");
Data<int> c(2);
std::cout << "10 < \"2\"? " << std::boolalpha << ( a < b ) << std::endl;
std::cout << "10 < 2? " << std::boolalpha << ( a < c ) << std::endl;
return 0;
}
I was experimenting with a member operator<() versus a global-scoped operator<(). The former is demonstrated in the #if 1 block, and works as expected. When I try to force use of the latter by changing the #if 1 to #if 0, code no longer behaves as desired: the global-scope operator<() appears to not be invoked.
Can someone please point out why the global-scoped operator<() is not invoked/does not work, whereas the member operator<() does?
What is happening here is what #n.m. said in the comments. It took me a while to track down the precise reason why this happens, although it was pretty simple in the end.
When you consider operator overloading, there is a list of viable functions that gets generated and then gets passed to the algorithm that determines which out of those will be called. In particular for operator overloading the list of considered functions is this
16.3.1.2 Operators in expressions [over.match.oper/6]
The set of candidate functions for overload resolution is the union of the member candidates, the non-member candidates, and the built-in candidates.
cppreference explains it in more detail
For a unary operator # whose argument has type T1 (after removing cv-qualifications), or binary operator # whose left operand has type T1 and right operand of type T2 (after removing cv-qualifications), three sets of candidate functions are prepared:
1) member candidates:
2) non-member candidates:
3) built-in candidates:
And when overload resolution happens something special happens for member functions (emphasis mine)
If any candidate function is a member function (static or non-static), but not a constructor, it is treated as if it has an extra parameter (implicit object parameter) which represents the object for which they are called and appears before the first of the actual parameters.
So essentially the overloads you get for your case are
template <typename U>
bool operator<(EXACT_TYPE_PTR this, const Data<U>& cu );
template<typename T>
bool operator<(const Data<T>& a, const Data<T>& b)
Where EXACT_TYPE_PTR is replaced by the type of whichever object you decide to call operator< on. Now you have two candidates, one a template and another one that accepts one template parameter and one template argument. So naturally the one with the exact type is preferred, since it is an exact match
Note You should probably make the member operator<() function const, so that it can be more general and accept even const arguments. As it stands in the current case, if you have a const Data instance, then the non-member overload will be called

Storing member function pointer from arbitrary class as class instance variable

There are a few questions on SO that address passing function pointers as parameters/arguments (here, here, here, etc.). In fact, I asked a related question the other day. However, this question is a little different.
My problem is that I am writing a class that I want to be extremely flexible.
What I have now works for non-member functions. It is posted below
template <typename T>
class MyClass
{
private:
typedef double (*firstFunctionPtr) (const T &var);
typedef bool (*secondFunctionPtr)(const T &var);
// Function pointers as member variables
firstFunctionPtr _firstFunc;
secondFunctionPtr _secondFunc;
public:
inline MyClass(firstFunctionPtr firstFunc,
secondFunctionPtr secondFunc);
};
template<typename T>
MyClass<T>::MyClass(firstFunctionPtr firstFunc, secondFunctionPtr secondFunc) :
_firstFunc(firstFunc),
_secondFunc(secondFunc),
{}
However, this falls apart when I need to initialize with a pointer to a member function of some other, arbitrary, class, which, unfortunately for me, happens to be a common use case for my purposes.
This answer suggests that
In a proper C++ interface you might want to have a look at having your function take templated argument for function objects to use arbitrary class types.
However, I have not been able to make this compile. I've tried templating my typedefs (using the C++11 aliasing approach), and I've tried adding a second template parameter to the class to handle the calling class of those member functions, but neither approach has worked.
This Q/A seems to be getting towards what I'm trying to do, but I can't make heads or tails of it.
Can someone please explain how I might modify my class to handle arbitrary member functions pointers being passed in?
Furthermore, is it possible to make it so that it can handle either arbitrary member functions or non-member functions?
Lastly, is it possible to do this with templates?
For the record, I'm trying to avoid using the functional header, but it may be a fool's errand not to use it.
If you want MyClass to be a template that can hold both free function
pointers of types:
double (*)(const T &var);
bool (*)(const T &var);
for some parameter type T, or alternatively member-function
pointers of types:
double (C::*)(const T &var);
bool (C::*)(const T &var);
for some parameter types C and T then, MyClass must be parameterized
by both T and C and you require two specializations:
Where C is some non-class type
Where C is any class type
In case (1), the non-class type C cannot possibly have member functions,
so that one will implement the free-function pointer specialization.
In case (2), the class C could be one that has member functions, so that one
will implement the member-function pointer specialization.
The obvious choice for a non-class type C is void. So we can make C
default to void:
Primary template
template<typename T, typename C = void>
struct MyClass;
So that:
MyClass<T>
will be the free function pointer specialization for T, and:
MyClass<T,C>
for any C other than void, will be the member-function pointer specialization.
As you may know you can use std::enable_if
and SFINAE to make the compiler
chose one specialization of a class template or another, depending on whether one
of its template parameters U satisfies some compiletime test. You could take
that approach here, but another one is available that does not require that apparatus:
Starting with the primary template, we would just like to have:
Free function specialization
template<typename T>
struct MyClass<T>
{
... for free function pointers ...
};
and:
Member function specialization
template<typename T, typename C>
struct MyClass<T,C>
{
... for member function pointers ...
};
But we can't have just that, because the member function "specialization" has exactly
the same template parameters as the primary template. Which means it isn't
a specialization, and the compiler won't allow it.
You can easily remove that problem, however, simply by giving the primary
template one more defaulting template parameter that it doesn't need, but whose
presence allows both those specializations to stand.
New primary template
template <typename T, typename C = void, typename Default = void>
struct MyClass;
So here is an illustrative solution:
// Primary template
template <typename T, typename C = void, typename Default = void>
struct MyClass;
// Free function specialization
template <typename T>
struct MyClass<T>
{
using firstFunctor_t = double(*)(T const &);
using secondFunctor_t = bool(*)(T const &);
MyClass(firstFunctor_t firstFunc, secondFunctor_t secondFunc)
: _firstFunc(firstFunc),
_secondFunc(secondFunc)
{}
double callFirst(T const & var) {
return _firstFunc(var);
}
bool callSecond(T const & var) {
return _secondFunc(var);
}
private:
firstFunctor_t _firstFunc;
secondFunctor_t _secondFunc;
};
// Member function specialization
template <typename T, typename C>
struct MyClass<T,C>
{
using firstFunctor_t = double(C::*)(T const &);
using secondFunctor_t = bool(C::*)(T const &) const;
MyClass(firstFunctor_t firstFunc, secondFunctor_t secondFunc)
: _firstFunc(firstFunc),
_secondFunc(secondFunc)
{}
double callFirst(C & obj, T const & var) {
return (obj.*_firstFunc)(var);
}
double callFirst(C const & obj, T const & var) {
auto & o = const_cast<C&>(obj);
return (o.*_firstFunc)(var);
}
bool callSecond(C & obj, T const & var) {
return (obj.*_secondFunc)(var);
}
bool callSecond(C const & obj, T const & var) {
auto & o = const_cast<C&>(obj);
return (o.*_secondFunc)(var);
}
private:
firstFunctor_t _firstFunc;
secondFunctor_t _secondFunc;
};
In the member function specialization, notice a couple of points that you might
not have considered:-
I decided that the second member function I want to store shall be a
const member function. It's more than likely that a member function of C
that take a T const & argument and returns bool will be a const member
function, isn't it? And if so, then that const-ness has to be part of
the member-function type definition that I use in the specialization:
using secondFunctor_t = bool(C::*)(T const &) const;
or attempts to instantiate the specialization with any bool (C::*)(T const &) const
will fail to compile.
Also, I have provided two overloads for each of MyClass<T,C>::callFirst
and MyClass<T,C>::callSecond, one with arguments:
C & obj, T const & var
and another with arguments:
C const & obj, T const & var
Without the second, attempts to call either MyClass<T,C>::callFirst
or MyClass<T,C>::callSecond with an obj that is const will fail to
compile.
For program to demo this solution you can append:
#include <iostream>
#include <string>
double foo(std::string const & s)
{
return std::stod(s);
}
bool bar(std::string const & s)
{
return s.size() > 0;
}
struct SomeClass
{
SomeClass(){};
double foo(std::string const & s) {
return ::foo(s);
}
bool bar(std::string const & s) const {
return ::bar(s);
}
};
int main()
{
MyClass<std::string> my0{foo,bar};
std::cout << std::boolalpha;
std::cout << my0.callFirst("1.11") << std::endl;
std::cout << my0.callSecond("Hello World") << std::endl;
MyClass<std::string,SomeClass> my1{&SomeClass::foo,&SomeClass::bar};
SomeClass thing;
std::cout << my1.callFirst(thing,"2.22") << std::endl;
std::cout << my1.callSecond(thing,"Hello World") << std::endl;
SomeClass const constThing;
std::cout << my1.callFirst(constThing,"3.33") << std::endl;
std::cout << my1.callSecond(constThing,"Hello World") << std::endl;
return 0;
}
See it live
You said that you want this template to be "extremely flexible". The
illustrated solution is fitted to your example, but you might be
interested in know that it isn't nearly as flexible as you could get.
For both free functions and member functions, with additional variadic template
parameters, your template could store and call [member] functions with
arbitary return types and arbitary numbers of arguments of arbitrary types.
See this question and
answer.
I will sugest to create a helper object which will store the type you want to work with:
template <typename RETURN, typename TYPE, typename CLASS>
struct function_pointer
{ using type_t = RETURN (CLASS::*)(const TYPE &); };
template <typename RETURN, typename TYPE>
struct function_pointer<RETURN, TYPE, std::nullptr_t>
{ using type_t = RETURN (*)(const TYPE &); };
This type will create a member-function-pointer if a class is provided as third parameter and a function-pointer otherwise. Now, we can use this helper in MyClass:
template <typename T, typename CLASS = std::nullptr_t>
class MyClass
{
using firstFunctionPtr = typename function_pointer<double, T, CLASS>::type_t;
using secondFunctionPtr = typename function_pointer<bool, T, CLASS>::type_t;
// Function pointers as member variables
firstFunctionPtr _firstFunc;
secondFunctionPtr _secondFunc;
public:
inline MyClass(firstFunctionPtr firstFunc, secondFunctionPtr secondFunc) :
_firstFunc(firstFunc),
_secondFunc(secondFunc)
{}
void call_first(CLASS &c, const T&v) { (c.*_firstFunc)(v); }
void call_second(CLASS &c, const T&v) { (c.*_secondFunc)(v); }
void call_first(const T&v) { (_firstFunc)(v); }
void call_second(const T&v) { (_secondFunc)(v); }
};
I've added call_* functions just to show a use case, which will be as below:
// Some class with the expected function signatures
struct S1
{
int i = 0;
double d(const int &) { std::cout << i << ' ' << __PRETTY_FUNCTION__ << '\n'; return{}; }
bool b(const int &) { std::cout << i << ' ' << __PRETTY_FUNCTION__ << '\n'; return{}; }
};
// Another class with the expected function signatures
struct S2
{
double d(const int &) { std::cout << __PRETTY_FUNCTION__ << '\n'; return{}; }
bool b(const int &) { std::cout << __PRETTY_FUNCTION__ << '\n'; return{}; }
};
// Free function with which could have the expected function signature
template <typename R>
R f(const int &) { std::cout << __PRETTY_FUNCTION__ << '\n'; return{}; }
Using MyClass with an arbitrary class (S1):
S1 a{1}, b{2};
S2 c, d;
MyClass<int, S1> MCiS1(&S1::d, &S1::b);
MCiS1.call_first(a, 111); // Prints -> 1 double S1::d(const int&)
MCiS1.call_second(b, 222); // Prints -> 2 bool S1::b(const int&)
MCiS1.call_first(c, 111); // Error decltype(c) is not S1.
MCiS1.call_second(d, 222); // Error decltype(d) is not S1.
Using MyClass with a different class (S2):
MyClass<int, S2> MCiS2(&S2::d, &S2::b);
MCiS2.call_first(c, 111); // Prints -> double S2::d(const int&)
MCiS2.call_second(d, 222); // Prints -> bool S2::b(const int&)
MCiS2.call_first(a, 111); // Error decltype(c) is not S2.
MCiS2.call_second(b, 222); // Error decltype(d) is not S2.
Using MyClass with non-member functions:
MyClass<int> MCi(f<double>, f<bool>);
MCi.call_first(111); // Prints -> R f(const int&) [with R = double]
MCi.call_second(222); // Prints -> R f(const int&) [with R = bool]
Check the live demo Here.
All you need to do is bind the object instance for the member function pointer as a first argument.
struct foo {
float bar1(const type &var);
bool bar2(const type &var);
};
foo my_foo;
auto f1 = std::bind(&foo::bar1, my_foo, _1);
auto f2 = std::bind(&foo::bar2, my_foo, _1);
MyClass<type> my_obj(f1, f2);

How to implement a default operator<<(ostream&, T) for type without this operator?

Since std::to_string is added to c++11, I started implementing to_string instead of the more traditional operator<<(ostream&, T). I need to link the two together in order to incorporate libraries that rely on operator<<(ostream&, T). I want to be able to express that if T has operator<<(ostream&, T), use it; otherwise, use std::to_string. I am prototyping a more limited version that enables operator<< for all enum classes.
enum class MyEnum { A, B, C };
// plain version works
//std::ostream& operator<<(std::ostream& out, const MyEnum& t) {
// return (out << to_string(t));
//}
// templated version not working
template<typename T,
typename std::enable_if<std::is_enum<T>::value>::type
>
std::ostream& operator<<(std::ostream& out, const T& t) {
return (out << to_string(t));
}
Compiler says error: no match for 'operator<<' (operand types are 'std::ostream {aka std::basic_ostream<char>}' and 'MyEnum')
cout << v << endl;
Questions:
Why is the template function not found by the compiler?
Is there a way to implement the general solution?
The following will work if there exists a std::to_string that accepts an argument of type const MyEnum (which doesn't exist according to clang-703.0.31).
#include <iostream>
#include <type_traits>
enum class MyEnum { A, B, C };
template<typename T>
typename std::enable_if<std::is_enum<T>::value, std::ostream &>::type
operator<<(std::ostream& out, const T& t) {
return (out << std::to_string(t));
}
int main() {
MyEnum a;
std::cout << a << std::endl;
}
According to the docs, there are two ways of using std::enable_if, one of which is to make the return type of a function only valid if T is an enum type (in your case). This is what this code shows. If std::is_enum<T>::value is true, then std::enable_if<std::is_enum<T>::value, std::ostream &>::type results in std::ostream & and is not defined (which makes the compiler yell at you) otherwise.
You could probably write something like my::to_string which would try to convert to a string user-defined types as well:
namespace my {
template<typename T>
typename std::enable_if<! std::is_void<T>{} && std::is_fundamental<T>{}, std::string>::type
to_string(T t) {
return std::to_string(t);
}
std::string to_string(std::nullptr_t) = delete;
std::string to_string(MyEnum a) {
return "This is an enum";
}
}
Then, you can use my::to_string instead of std::to_string in your operator<<:
return (out << my::to_string(t));
EDIT: using my::to_string now results in a compilation error when it's argument is void or std::nullptr_t.
Why your code didn't work
Look at the example in the docs:
// 2. the second template argument is only valid if T is an integral type:
template < class T,
class = typename std::enable_if<std::is_integral<T>::value>::type>
bool is_even (T i) {return !bool(i%2);}
As you can see, the second template argument is written with class = /* enable_if stuff */, but in your code you do simply template< typename T, /* enable_if stuff */ >. So, if you follow the docs, you'll get the correct result - the compiler will say it couldn't find a specialization of std::to_string that accepted an enum as a parameter.

Template function default parameter

//template.h using MSVC++ 2010
#pragma once
#include <iostream>
using std::ostream;
template <typename T, typename U> class Pair {
private:
T first;
U second;
public:
// Pair() ;
Pair ( T x = T() , U y = U() ) ;
template<typename T, typename U>
friend ostream& operator<< ( ostream& thisPair, Pair<T, U>& otherPair );
};
template <typename T, typename U>
Pair<T, U>::Pair ( T x , U y ) : first ( T ( x ) ), second ( U ( y ) )
{cout << x << y;}
template <typename T, typename U>
ostream& operator<< ( ostream& os, Pair<T, U>& otherPair )
{
os << "First: " << otherPair.first
<< " "<< "Second: " << otherPair.second << endl;
return os;
}
//template.cpp
int main()
{
int a = 5, b = 6;
Pair<int,int> pair4();
Pair<int, int> pair1 ( a, b );
cout<<pair4;
cout<<pair1;
return 0;
}
How to make a constructor or a member function to take default value?
The code above is giving linker error for pair4 when using cout statement.
The code works perfectly when cout<<pair4(); is commented.
I am trying to mimic a constructor taking 0,1 or 2 argument using a single default constructor in a template class.
Apart from other errors like shadowing template parameters (which MSVC++ wrongly ignores), the problem is here:
Pair<int,int> pair4();
This declares a function instead of a variable. This is because it can be syntactically both and C++ standard selects the most vexing parse: anything that can be interpreted by compiler as a declaration, will be interpreted as a declaration. The linker error then is that you try to print to cout address of a function that is never defined (has no address).
Side note: in GCC and Clang, you can actually link this because the address is immediatelly converted to bool for operator << (there is no operator for printing function pointers to ostream and bool is the only available implicit conversion) which will always result in true (address of a declared function can never be nullptr) so the address itself is optimized away.
The fix is very simple:
Pair<int,int> pair4;