Here is the problem I am facing: I have an overloaded function in a class, and I want to pass one of its overloads as a parameter. But when doing so, I get the following error :
"no suitable constructor exists to convert from <unknown-type> to std::function<...>"
Here's a code sample to illustrate that :
#include <functional>
#include <string>
class Foo
{
private:
int val1 , val2;
};
class Bar
{
public:
void function ( ) {
//do stuff;
Foo f;
function ( f );
}
void function ( const Foo& f ) {
//do stuff
}
private:
//random attribute
std::string str;
};
void otherFunction ( std::function<void ( Bar& , const Foo& ) > function ) {
Bar b;
Foo f;
function(b,f);
}
int main ( ) {
otherFunction ( &Bar::function );
^^^
error
}
I understand that the compiler cannot deduce which overload to use, so the next best thing to do is a static_cast
, but the following code still has the same error
std::function<void ( Bar& , const Foo& )> f = static_cast< std::function<void ( Bar& , const Foo& )> > ( &Bar::function );
You need to cast to member-function pointer, not to std::function
:
otherFunction ( static_cast<void(Bar::*)(const Foo&)>(&Bar::function) );
Live
[EDIT]
Explanation:
otherFunction ( &Bar::function );
otherFunction
takes std::function
as a parameter. std::function
has an implicit constructor (an implicit conversion) from a function pointer (a member function or a free function, and other "callable" types, doesn't matter here). It looks like this:
template< class F >
function( F f );
F
is "callable", it doesn't specify the signature of F
This means that compiler doesn't know which Bar::function
you meant, because this constructor doesn't put any restrictions on input parameter. That's what compiler is complaining about.
You tried
static_cast< std::function<void ( Bar& , const Foo& )> > ( &Bar::function );
While it looks like compiler has all details it needs here (the signature), actually the same constructor is called, so nothing effectively changed. (Actually, the signature is incorrect, but even correct one wouldn't work)
By casting to a function pointer we provide its signature
static_cast<void(Bar::*)(const Foo&)>(&Bar::function)
So ambiguity is resolved as there's only one such function so compiler is happy.
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