Как да извикам указател към членска функция, когато е член на клас данни?

struct B
{
  void (B::*pf)(int, int);  // data member
  B () : pf(&B::foo) {}
  void foo (int i, int j) { cout<<"foo(int, int)\n"; } // target method
};

int main ()
{
  B obj;
  // how to call foo() using obj.pf ?
}

В горния тестов код pf е член на данните на B. Какво е граматическото правило за извикването му? Трябва да е право напред, но не получавам правилно съвпадение. напр. Ако опитам obj.*pf(0,0);, получавам:

error: must use ‘.*’ or ‘->*’ to call pointer-to-member function in ‘pf (...)’, e.g. ‘(... ->* pf) (...)’

person iammilind    schedule 11.06.2011    source източник
comment
вижте: ideone.com/p3a5G   -  person Geoffroy    schedule 11.06.2011
comment
възможен дубликат на Извикване на методи на клас C++ чрез указател на функция   -  person Ciro Santilli 新疆再教育营六四事件ۍ    schedule 01.07.2015
comment
@CiroSantilli六四事件法轮功纳米比亚威视, Не и двете са различни. Вашият свързан въпрос обяснява, "How to call class member using function pointer?", докато аз питам "<...same...>, when the function pointer itself is a class member also.". Забележете, че отговорите и на двата въпроса са различни.   -  person iammilind    schedule 01.07.2015
comment
Съгласен съм, че това има една допълнителна стъпка. но чувствах, че може лесно да се изведе, след като знаете синтаксиса на указателя на функцията: (obj.*ptr), само това тук ptr == (obj.ptr). Но добре, тъй като не сте съгласни, ще се оттегля ;-)   -  person Ciro Santilli 新疆再教育营六四事件ۍ    schedule 01.07.2015


Отговори (3)


Като този:

(obj.*obj.pf)(0, 1);

Членският достъп (.) има по-висок приоритет от указател към членски оператор, така че това е еквивалентно на:

(obj.*(obj.pf))(0, 1);

Тъй като извикването на функция също има по-висок приоритет от указател към оператор член, не можете да направите:

obj.*obj.pf(0, 1) /* or */ obj.*(obj.pf)(0, 1)

Тъй като това би било еквивалентно на:

obj.*(obj.pf(0, 1)) // grammar expects obj.pf to be a callable returning a
                    // pointer to member
person CB Bailey    schedule 11.06.2011
comment
+1, благодаря; това е уникално; какво щеше да се случи, ако obj беше член на B? :) - person iammilind; 11.06.2011
comment
@iammilind: obj има тип B, така че не може да бъде член на B, тъй като това би означавало рекурсивна дефиниция на клас. Можете ли да поясните какво имате предвид? - person CB Bailey; 11.06.2011
comment
Не, дори ако имаше член като obj вътре в B; няма да е проблем, докато не (....) поставите подписа. Вече съм наясно с този проблем. Така че или ще бъде грешка при компилиране, или ще работи добре. - person iammilind; 11.06.2011

pf е указател на метод и вие искате да извикате метода, към който сочи, така че трябва да използвате

(obj.*obj.pf)(1, 2);

Той казва, че обектът obj извиква метода, посочен от pf

Вижте резултата тук:

http://ideone.com/p3a5G

person Geoffroy    schedule 11.06.2011

Синтаксисът е доста неестествен, но е следствие от правилата за приоритет на C++...

(obj.*obj.pf)(1, 2);
person 6502    schedule 11.06.2011