The following code snippet:
#include <iostream>
void does() { std::cout << "do" << std::endl; }
void does(bool b = false) { std::cout << "do(bool)" << std::endl; }
void fwd(void (*func)(bool))
{
func(false);
}
int main(int, char**)
{
fwd(&does);
fwd(does);
fwd(*does);
}
understandably produces the following error:
test.cpp:15:10: error: overloaded function with no contextual type information
The compiler cannot discern which of the functions I intend to use. What I don't understand is why the code will correctly run when I comment out the line that reads:
fwd(*does)
Why can the compiler suddenly resolve the ambiguousness?
int main(int, char**)
{
fwd(&does);
fwd(does);
}
Also, without overloading does
the snippet will correctly run with all 3 calls.
This snippet runs fine...
#include <iostream>
void does(bool b = false) { std::cout << "do(bool)" << std::endl; }
void fwd(void (*func)(bool))
{
func(false);
}
int main(int, char**)
{
fwd(&does);
fwd(does);
fwd(*does);
}
I'm compiling this with gcc 4.6.3 on a Linux box.
Thanks for the help!
The answer to your question is in the overload-resolution rules for functions.
Specifically, there is an exception for using &
before the function-name (once) not breaking overload-resolution, but none for using *
.
Also see that only one of those two functions accept that single argument:
13.4 Address of overloaded function
[over.over]
1 A use of an overloaded function name without arguments is resolved in certain contexts to a function, a pointer to function or a pointer to member function for a specific function from the overload set. A function template name is considered to name a set of overloaded functions in such contexts. The function selected is the one whose type is identical to the function type of the target type required in the context. [ Note: That is, the class of which the function is a member is ignored when matching a pointer-to-member-function type. —end note ] The target can be
- an object or reference being initialized (8.5, 8.5.3),
- the left side of an assignment (5.17),
- a parameter of a function (5.2.2),
- a parameter of a user-defined operator (13.5),
- the return value of a function, operator function, or conversion (6.6.3),
- an explicit type conversion (5.2.3, 5.2.9, 5.4), or
- a non-type template-parameter (14.3.2).
The overloaded function name can be preceded by the
&
operator. An overloaded function name shall not be used without arguments in contexts other than those listed.
Quote is from n3242 (c++11), with bold by me.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With