Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What is the difference between &foo::function and foo::function?

I am using the gtkmm library on linux to draw a simple menu for my GUI.

In the below code the compiler complained about unable to resolve address

        sigc::mem_fun(*this, AppWindow::hide)));
                                         ^
appwindow.cpp:15:41: note:   could not resolve address from overloaded function

But when I insert the & it compiles fine

m_menu_app.items().push_back(MenuElem("Quit",
    sigc::mem_fun(*this, &AppWindow::hide)));

What difference does it make here? Isn't the hide function just an address in the first place?

like image 732
Mark Avatar asked Jan 09 '15 21:01

Mark


People also ask

What is the definition of the difference between?

The difference between two things is the way in which they are unlike each other.

What is difference between among and between?

The most common use for among is when something is in or with a group of a few, several, or many things. The most common use of between is when something is in the middle of two things or two groups of things. It is sometimes used in the phrase in between.

What is the difference between difference and differentiation?

To differ means to be different. To differentiate means to make (someone or something) different in some way.


2 Answers

This is the exact definition of the function-to-pointer conversion, [conv.func]:

An lvalue of function type T can be converted to a prvalue of type “pointer to T.” The result is a pointer to the function.55


55)This conversion never applies to non-static member functions because an lvalue that refers to a non-static member function cannot be obtained.

Thus the decay that we see with normal, non-member functions1 doesn't apply and you need to explicitly take the address.

I.e.

void f();

struct A {
    void f();
    static void g();
};


auto a = f; // Ok: auto deduced as void(*)()
auto b = A::f; // Error: A::f not an lvalue, auto cannot be deduced
auto c = A::g; // Ok: auto deduced as void(*)()


1 Or static member functions.
like image 168
Columbo Avatar answered Sep 25 '22 07:09

Columbo


For global (non-member) functions, the name of the function evaluates to the address of that function except when passed to the & operator, so you can (for example) assign to a pointer to a function either with or without the & equivalently:

int f() {}

int (*pf1)() = f;
int (*pf2)() = &f;

So, in this case there's really no difference between the two.

For member functions1, however, the rules are a bit different. In this case, the & is required; if you attempt to omit the &, the code simply won't compile (assuming a properly functioning compiler, anyway).

There's no particular reason this would have to be the case--it's just how Bjarne decided things should be. If he'd decided he wanted the name of a member function to evaluate to a pointer to a member (equivalent to how things work for non-member functions) he could have done that.


1. Other than static member functions, which mostly act like non-member functions.

like image 22
Jerry Coffin Avatar answered Sep 26 '22 07:09

Jerry Coffin