A problem about a pointer to member function?

Started by
10 comments, last by bluepig.man 11 years, 4 months ago
L have declare two function like this:

[source lang="cpp"]void order( void (*visit) (int,int) );
void visit(int,int);[/source]

They are member function in the same class?
And l want call order like this:

[source lang="cpp"]oder(visit);[/source]

but it can't pass.
How can l do this?
Advertisement
void (MyClass::*visit) (int,int)

https://www.kbasm.com -- My personal website

https://github.com/wqking/eventpp  eventpp -- C++ library for event dispatcher and callback list

https://github.com/cpgf/cpgf  cpgf library -- free C++ open source library for reflection, serialization, script binding, callbacks, and meta data for OpenGL Box2D, SFML and Irrlicht.

You're using a regular pointer-to-function, not a pointer-to-member-function.
The syntax for pointer-to-member-functions looks like:

class Foo
{
public:
void order( void (Foo::*visit) (int,int) )
{
(this->*visit)(1,2);
}
void visit(int x, int y)
{
printf("%d, %d\n", x, y);
}
void test()
{
order(&Foo::visit);
}
};


(this->*visit)(1,2);


thank s for your answer,but what's the meaning of this?
That's the syntax for calling a pointer-to-member-function.

It's a bit confusing because you've called both a variable and a function "visit", so I'll pretend the [font=courier new,courier,monospace]order[/font] definition is instead:
[font=courier new,courier,monospace]void order( void (Foo::*fn) (int,int) )[/font]

"[font=courier new,courier,monospace]fn[/font]" is a pointer, so "[font=courier new,courier,monospace]*fn[/font]" dereferences that pointer as usual. [font=courier new,courier,monospace]fn[/font] was a pointer-to-member-function, so [font=courier new,courier,monospace]*fn[/font] is just a member-function.
i.e. [font=courier new,courier,monospace]fn[/font] is "[font=courier new,courier,monospace]&Foo::visit[/font]" and [font=courier new,courier,monospace]*fn[/font] is "[font=courier new,courier,monospace]Foo::visit[/font]"

"[font=courier new,courier,monospace]object->[/font]" is the regular syntax for accessing members of an object.
Normally you don't have to write "[font=courier new,courier,monospace]this->[/font]" in front of members, but you can if you want to -- e.g. in [font=courier new,courier,monospace]test[/font] you could write "[font=courier new,courier,monospace]this->order(blah);[/font]" and it would mean the same as "[font=courier new,courier,monospace]order(blah);[/font]".

So going off the above, [font=courier new,courier,monospace](this-> *fn)[/font] ends up meaning [font=courier new,courier,monospace]this->visit[/font], which is the same as just saying [font=courier new,courier,monospace]visit[/font].
We need to wrap it in parenthesis ([font=courier new,courier,monospace]()[/font]) and have to include the "[font=courier new,courier,monospace]this->[/font]" because of the weird way that pointer-to-member-function syntax works ;)

So then, [font=courier new,courier,monospace](this-> *fn)(1, 2)[/font] is the same as [font=courier new,courier,monospace]visit(1,2)[/font], which ends up printing "[font=courier new,courier,monospace]1 2[/font]".

[edit]As wqking corrected below "[font=courier new,courier,monospace]-> *[/font]" shouldn't have a space in it and should be "[font=courier new,courier,monospace]->*[/font]"

So going off the above, [font=courier new,courier,monospace](this-> *fn)[/font] ends up meaning [font=courier new,courier,monospace]this->visit[/font], which is the same as just saying [font=courier new,courier,monospace]visit[/font].


I think -> * should be ->* because it's a single operator and we can even overload it.

OP, try to Google for "c++ pointer to member operator", no quote mark.
Here are some search results,
http://msdn.microsoft.com/en-us/library/k8336763%28v=vs.80%29.aspx
http://stackoverflow.com/questions/6586205/what-are-the-pointer-to-member-and-operators-in-c

And Hodgman's reply. :-)

https://www.kbasm.com -- My personal website

https://github.com/wqking/eventpp  eventpp -- C++ library for event dispatcher and callback list

https://github.com/cpgf/cpgf  cpgf library -- free C++ open source library for reflection, serialization, script binding, callbacks, and meta data for OpenGL Box2D, SFML and Irrlicht.

I highly, highly recommend looking into Boost function (http://www.boost.org/doc/libs/1_52_0/doc/html/function.html). I use it for some callbacks and it works wonders.
l got the point.Thanks for the answer,

I highly, highly recommend looking into Boost function (http://www.boost.org/doc/libs/1_52_0/doc/html/function.html). I use it for some callbacks and it works wonders.


Or std::function and/or lambdas on C++11 capable compilers.
You are probably much better off learning about 'Interfaces' to solve this problem if you are going to use a pointer-to-a-member-function to solve it.


class ITweakable
{
public:
void TweakMe(void) = 0;
}

class Tweakie : ITweakable, IThwackable, //etc...
{
public:
void TweakMe(void)
{
g_Audio->StartPlayback('giggle.ogg');
}
void ThwackMe(void)
{
g_Audio->StartPlayback('oouff.ogg');
}
}

class TweakHerder
{
public:
AddTweakie(ITweakable* tweakie)
{
this->myTweakies.push_back(tweakie);
}
void TimeToTickleTheTweakies(void)
{
//Not C++ because C++ syntax for this is dog-pile
foreach(ITweakable* tweakie in myTweakies)
{
tweakie->TweakMe();
}
}
private:
list<ITweakable> myTweakies;
}


And there ya' go, entertainment for a toddler for hours.
- The trade-off between price and quality does not exist in Japan. Rather, the idea that high quality brings on cost reduction is widely accepted.-- Tajima & Matsubara

This topic is closed to new replies.

Advertisement