2017-02-22 3 views
8

Мне трудно вызвать указатель на функцию-член на объекте, который был отличен из void*. Ниже пример:Не удается вызвать указатель на функцию-член из статического метода

class Test 
{ 
public: 
    Test(int pointTo) 
    { 
     if (pointTo == 1) 
      function = &Test::Function1; 
     else 
      function = &Test::Function2; 
    } 

    static void CallIt(void* cStyle) 
    { 
     Test* t(static_cast<Test*>(cStyle)); 
     (t->*function)();// error C2568: '->*': unable to resolve function overload 
    } 

    void CallIt() 
    { 
     (this->*function)();// Works just fine 
    } 

private: 
    typedef void (Test::*ptrToMemberFunc)(); 

    ptrToMemberFunc function; 

    void Function1() 
    { 
     std::cout << "Function 1" << std::endl; 
    } 

    void Function2() 
    { 
     std::cout << "Function 2" << std::endl; 
    } 
}; 

int main() 
{ 
    Test t1(1); 
    Test t2(2); 

    Test::CallIt(static_cast<void*>(&t1)); 
    Test::CallIt(static_cast<void*>(&t2)); 

    t1.CallIt(); 
    t2.CallIt(); 

    return 0; 
} 

Что происходит, когда объект приведен к void* и обратно? Почему я больше не могу вызвать указатель на функцию-член?

EDIT:

CallIt() Изменение следующим образом позволяет программе компиляции, но я до сих пор интересно, почему оригинал не работает.

static void CallIt(void* cStyle) 
{ 
    Test* t(static_cast<Test*>(cStyle)); 
    Test::ptrToMemberFunc pf(t->function); 
    (t->*pf)(); 
} 
+0

это смешно, что я только что написал точно такой же код в wandbox, вплоть до identificatiors. Ответ Tuple_cat объясняет это. В основном вам нужно связать объект и вызываемый, поэтому одного оператора косвенности недостаточно. Некоторые компиляторы дают более понятные сообщения об ошибках, например, они говорят вам, что вы можете вызвать только статический член таким образом - намек на то, что у вас не было указателя для них. – Swift

+0

Что касается вашего редактирования, я просто думаю, что внешний вид оператора ' > * 'отбрасывает вас. Полагайте, что это была обычная функция с именем 'call_with_this', которая взяла указатель на объект и функцию-член. Тогда ваш оригинальный нерабочий вызов был 'call_with_this (t, function);'. Здесь так просто имя 'function' является нестатическим членом класса' Test', но это не имеет никакого отношения к 't'. И поскольку вы находитесь в статической функции, нет «этого», чтобы найти имя 'function'. Когда вы попросите 't-> function', вы получите фактическое значение с доступным именем. – GManNickG

+0

@GManNickG Вот именно это. Теперь, когда я вижу решение, я понял, но я не понимал, что фактически делает оператор '-> *' (я читал его как '(t -> (* function))'). – Kerry

ответ

10
main.cpp:17:14: error: invalid use of member 'function' in static member function 
     (t->*function)();// error C2568: '->*': unable to resolve function overload 
      ^~~~~~~~ 

function не является статическим членом данных, так что вы не можете получить доступ к нему из статической функции.

Если вы хотите обратиться к functiont «s, вы можете сделать это так:

 (t->*(t->function))(); 
+0

Это по той же причине, почему он вынужден писать '(this -> * function)()' в нестационарном члене, самый внутренний оператор направления «получает» значение указателя, а самый дальний позволяет вызвать ссылку на объект – Swift

Смежные вопросы