Velocity Reviews

Velocity Reviews (http://www.velocityreviews.com/forums/index.php)
-   C++ (http://www.velocityreviews.com/forums/f39-c.html)
-   -   Figure out why member function pointer doesn't work? (http://www.velocityreviews.com/forums/t746191-figure-out-why-member-function-pointer-doesnt-work.html)

Nephi Immortal 04-02-2011 01:15 AM

Figure out why member function pointer doesn't work?
 
Please look at my code below. You may notice operator->* with
comments. Figure out why it does not make any sense.

struct data;
typedef void ( data::*pGo )();

struct data {
char x;
char y;
pGo Go;

void Run() {
}
};

struct storage {
data *pData;

data *operator->() {
return pData;
}

storage &operator->*( pGo p ) {
( pData->*p )();
return *this;
}
};

int main()
{
data d; storage s;
s.pData = &d;
s->x = 1; s->y = 2; s->Go = &data::Run;

( d.* d.Go )(); // OK
( d.* s->Go )(); // OK

s.operator->*( s->Go ); // ??? Works fine
s->*( s->Go ); // ??? Works fine

( s->* s->Go )(); // Should be, but does not work!

return 0;
}

Victor Bazarov 04-02-2011 02:55 AM

Re: Figure out why member function pointer doesn't work?
 
On 4/1/2011 9:15 PM, Nephi Immortal wrote:
> Please look at my code below. You may notice operator->* with
> comments. Figure out why it does not make any sense.
>
> struct data;
> typedef void ( data::*pGo )();
>
> struct data {
> char x;
> char y;
> pGo Go;
>
> void Run() {
> }
> };
>
> struct storage {
> data *pData;
>
> data *operator->() {
> return pData;
> }
>
> storage&operator->*( pGo p ) {
> ( pData->*p )();
> return *this;
> }
> };
>
> int main()
> {
> data d; storage s;
> s.pData =&d;
> s->x = 1; s->y = 2; s->Go =&data::Run;
>
> ( d.* d.Go )(); // OK
> ( d.* s->Go )(); // OK
>
> s.operator->*( s->Go ); // ??? Works fine
> s->*( s->Go ); // ??? Works fine
>
> ( s->* s->Go )(); // Should be, but does not work!


What do you mean by "does not work"? Does it compile? If not, what's
the error message, what in it is unclear? If it does compile, do you
get an error when running?

Have you checked operator precedence? Can you place the parentheses in
the last expression to indicate how you think it should be evaluated?
Does it "work" after that? What's different (if anything) when you add
parentheses?

>
> return 0;
> }


V
--
I do not respond to top-posted replies, please don't ask

Qi 04-02-2011 03:05 AM

Re: Figure out why member function pointer doesn't work?
 
On 2011-4-2 9:15, Nephi Immortal wrote:
> ( s->* s->Go )();


"( s->* s->Go )(); "
==
(( s->* s)->Go )();

So it won't compile.


--
WQ

Nephi Immortal 04-02-2011 03:42 AM

Re: Figure out why member function pointer doesn't work?
 
On Apr 1, 9:55*pm, Victor Bazarov <v.baza...@comcast.invalid> wrote:
> On 4/1/2011 9:15 PM, Nephi Immortal wrote:
>
>
>
>
>
> > * *Please look at my code below. *You may notice operator->* with
> > comments. *Figure out why it does not make any sense.

>
> > struct data;
> > typedef void ( data::*pGo )();

>
> > struct data {
> > * *char x;
> > * *char y;
> > * *pGo Go;

>
> > * *void Run() {
> > * *}
> > };

>
> > struct storage {
> > * *data *pData;

>
> > * *data *operator->() {
> > * * * * * *return pData;
> > * *}

>
> > * *storage&operator->*( pGo p ) {
> > * * * * * *( pData->*p )();
> > * * * * * *return *this;
> > * *}
> > };

>
> > int main()
> > {
> > * *data d; storage s;
> > * *s.pData =&d;
> > * *s->x = 1; s->y = 2; s->Go =&data::Run;

>
> > * *( d.* d.Go )(); // OK
> > * *( d.* s->Go )(); // OK

>
> > * *s.operator->*( s->Go ); // ??? Works fine
> > * *s->*( s->Go ); // ??? Works fine

>
> > * *( s->* s->Go )(); // Should be, but does not work!

>
> What do you mean by "does not work"? *Does it compile? *If not, what's
> the error message, what in it is unclear? *If it does compile, do you
> get an error when running?
>
> Have you checked operator precedence? *Can you place the parentheses in
> the last expression to indicate how you think it should be evaluated?
> Does it "work" after that? *What's different (if anything) when you add
> parentheses?


Victor,

You asked the same questions. I searched using google operator->*
across websites. There are a lot of operator->, but nothing showed
operator->*. There is no book mentioned it either.
I can say operator->* is rarely used. Please do a favor for me. Do
your homework to do research? Okay? If you succeed, the information
should be added to the book. You will be author as C++ book writer.


>
>
>
> > * *return 0;
> > }

>
> V
> --
> I do not respond to top-posted replies, please don't ask- Hide quoted text -
>
> - Show quoted text -



James Kanze 04-03-2011 04:54 PM

Re: Figure out why member function pointer doesn't work?
 
On Apr 2, 2:15 am, Nephi Immortal <immortalne...@gmail.com> wrote:
> Please look at my code below. You may notice operator->* with
> comments. Figure out why it does not make any sense.


> struct data;
> typedef void ( data::*pGo )();


> struct data {
> char x;
> char y;
> pGo Go;
>
> void Run() {
> }
> };


> struct storage {
> data *pData;


> data *operator->() {
> return pData;
> }


> storage &operator->*( pGo p ) {


Here you define an operator->* which takes a storage and a
data::*pGo, and returns a storage. Why? What are you trying to
achieve.

> ( pData->*p )();
> return *this;
> }
> };


> int main()
> {
> data d; storage s;
> s.pData = &d;
> s->x = 1; s->y = 2; s->Go = &data::Run;


> ( d.* d.Go )(); // OK
> ( d.* s->Go )(); // OK


> s.operator->*( s->Go ); // ??? Works fine
> s->*( s->Go ); // ??? Works fine


> ( s->* s->Go )(); // Should be, but does not work!


s->*s->Go returns a storage&. You then try to call it as a
function. Since storage has no overloaded operator(), it fails.
What do you expect?

> return 0;
> }


--
James Kanze

Nephi Immortal 04-05-2011 01:41 AM

Re: Figure out why member function pointer doesn't work?
 
On Apr 3, 11:54*am, James Kanze <james.ka...@gmail.com> wrote:
> On Apr 2, 2:15 am, Nephi Immortal <immortalne...@gmail.com> wrote:
>
>
>
>
>
> > Please look at my code below. *You may notice operator->* with
> > comments. *Figure out why it does not make any sense.
> > struct data;
> > typedef void ( data::*pGo )();
> > struct data {
> > * * * * char x;
> > * * * * char y;
> > * * * * pGo Go;

>
> > * * * * void Run() {
> > * * * * }
> > };
> > struct storage {
> > * * * * data *pData;
> > * * * * data *operator->() {
> > * * * * * * * * return pData;
> > * * * * }
> > * * * * storage &operator->*( pGo p ) {

>
> Here you define an operator->* which takes a storage and a
> data::*pGo, and returns a storage. *Why? *What are you trying to
> achieve.
>
> > * * * * * * * * ( pData->*p )();
> > * * * * * * * * return *this;
> > * * * * }
> > };
> > int main()
> > {
> > * * * * data d; storage s;
> > * * * * s.pData = &d;
> > * * * * s->x = 1; s->y = 2; s->Go = &data::Run;
> > * * * * ( d.* d.Go )(); // OK
> > * * * * ( d.* s->Go )(); // OK
> > * * * * s.operator->*( s->Go ); // ??? Works fine
> > * * * * s->*( s->Go ); // ??? Works fine
> > * * * * ( s->* s->Go )(); // Should be, but does not work!

>
> s->*s->Go returns a storage&. *You then try to call it as a
> function. *Since storage has no overloaded operator(), it fails.
> What do you expect?
>
> > * * * * return 0;
> > }


James,

Do you know how to implement operator->* like I wrote operator->?
Operator->* and operator-> are very similar. Why canít I use operator-
>* to call struct dataís member function to pointer?


SG 04-05-2011 07:22 AM

Re: Figure out why member function pointer doesn't work?
 
On 5 Apr., 03:41, Nephi Immortal wrote:
> Operator->* and operator-> are very similar. *Why canít I use
> operator->* to call struct dataís member function to pointer?


First of all, you need to recognize that the precedence of operator->
is higher than of the operator->*:

x->y->z is grouped like this: (x->y)->z

while

x->*y->z is grouped like this: x->*(y->z)

Secondly, what you are trying to do cannot work without a proxy
callable object. In order to make

(x->*y)();

work your operator->* function would need to return something that is
callable. Unfortunately, the result of ptr->*pmemfun where ptr is a
raw pointer and pmemfun is a member function pointer can only be used
as operand for the function call operator. You cannot return the
result of ptr->*pmemfun from a function and delay the function call
this way. C++ does not allow this.

If you want to support operator->* to be able to invoke member
functions you could try somehting like this:

struct bound_data_memfun {
data* ptr;
pGo pmemfun;
void operator()() const {return (ptr->*pmemfun)();}
// ^^^^^^^^^^^^^
// can only be used in combinaton with the function call
// operator.
};

struct storage {
...
bound_data_memfun operator->*(pGo pmemfun)
{
bound_data_memfun result = {pData,pmemfun};
return result;
}
...
};

IMHO it's not worth the hassle, though. None of the popular smart
pointer classes overload the operator->* and there is no harm in that.
Simply write

((*x).*y)();

and be done.

SG

SG 04-05-2011 08:10 AM

Re: Figure out why member function pointer doesn't work?
 
On 5 Apr., 09:22, SG wrote:
> On 5 Apr., 03:41, Nephi Immortal wrote:
>
> > Operator->* and operator-> are very similar. *Why canít I use
> > operator->* to call struct dataís member function to pointer?

>
> First of all, you need to recognize that the precedence of operator->
> is higher than of the operator->*:
>
> * x->y->z * is grouped like this: *(x->y)->z
>
> while
>
> * x->*y->z *is grouped like this: *x->*(y->z)


the relevant cases here are actually

x->y() is equiv to (x->y)()
x->*y() is equiv to x->*(y()) AND NOT to (x->*y)()

Operators -> and () form postfix expression while ->* and .* are
pointer-to-member operators with a lower precedence. Also:

" 5.5 Pointer-to-member operators [expr.mptr.oper]
[...]
6 If the result of .* or ->* is a function, then that result can
only be used as operand for the function call operator (). "

SG


All times are GMT. The time now is 06:46 AM.

Powered by vBulletin®. Copyright ©2000 - 2014, vBulletin Solutions, Inc.
SEO by vBSEO ©2010, Crawlability, Inc.