When I compile the following code with MSVC++, I get an error:
struct A
{
template<typename T>
void operator<<(T&& x)
{
}
};
void f()
{
}
int main()
{
A().operator<<( f ); // ok
A() << f; // error
return 0;
}
g++ and clang both compile this code fine. AFAIK, 'ok' and 'error' lines do exactly the same thing, and type T is deduced to void(&)(). Or is it void() and rvalue references to function are allowed? If so, what is their meaning? Is it ok to pass functions by reference like that? Is it MSVC++ bug that it fails to compile 'error' line? BTW, the error output:
no operator found which takes a right-hand operand of type 'overloaded-function' (or there is no acceptable conversion)
could be 'void A::operator <<<void(void)>(T (__cdecl &&))'
with[ T=void (void) ]
So, answering my own question:
The code provided is valid and while rvalue references to functions are allowed (they act identical to lvalue references), here during template deduction T should become void(&)().
A bug in MSVC prevents my code from compiling.
UPDATE: The bug has been fixed in Visual Studio 2013 compiler