2012-06-25 3 views
1

Есть несколько примеров, но пока я не могу понять решение моей проблемы. У меня естьПередача указателя на функцию-член

class FooSource{ 
    ... 

    void StartGetFoos(void (*callback)(vector<IFoo*>*, IAsyncResult)); 
    ... 
} 

Когда StartGetFoos() называется, запрос это сделано, чтобы получить FOOS, сохраняя функцию обратного вызова. когда запрос завершается (занимает около 30 секунд), сохраненный обратный вызов вызывается с результатами. Я не могу изменить подпись этого метода.

и где-то у меня есть класс

class FooUser { 
    ... 

    void FooUser::MyCallback(vector<IFoo*>* foos, IAsyncResult result) 
    { 
      // marshall to UI thread and update UI 
    } 

    void init() 
    { 
     fooUser->StartGetFoos(??????); 
     // how do I pass my callback member function here? 
    } 
} 
+0

родственный: http://stackoverflow.com/questions/1738313/c-using-class-method-as-a-function-pointer-type –

ответ

3

Там нет нигде на подпись void (*callback)(vector<IFoo*>*, IAsyncResult) для вас, чтобы получить this указатель, так что вы не можете использовать функцию-член. Вместо этого вы должны будете использовать функцию в static члена:

class FooUser { 
    static void MyCallback(vector<IFoo*>* foos, IAsyncResult result) 
    { 
      // marshall to UI thread and update UI 
    } 

    void init() 
    { 
     fooUser->StartGetFoos(&FooUser::MyCallback); 
    } 
}; 

Проблема здесь в том, что вы не сможете получить доступ к любым данным экземпляра на FooUser; это может быть или не быть проблемой.

В зависимости от того, насколько хорошо разработан API, может быть способ передачи указателя экземпляра, например. через IAsyncResult result.

+0

Можете ли вы расширить о том, как использовать статическую функцию-член в Это дело? Я раньше смотрел [этот пост] (http://stackoverflow.com/questions/400257/how-can-i-pass-a-class-member-function-as-a-callback) и выглядел многообещающим, но я мог Я не могу трансформировать ситуацию в свою ситуацию. Спасибо за помощь. –

+1

@ProfessorChaos, используйте статическую функцию-член для вызова другой нестатической функции-члена. Для этого статической функции нужно получить указатель объекта откуда-то, возможно, статическую переменную-указатель, если у вас никогда не было более одного обратного вызова. –

2

Если IAsyncResult - это структура данных, которые передаются, а затем снова возвращается к операции, вы можете расширить ее с помощью собственной информации.

class MyAsyncResult : public IAsyncResult 
{ 
public: 
    MyAsyncResult(FoorUser *sender) : sender(sender){} 
    FooUser *sender; 
}; 

Тогда, как говорит ecatmur, вы можете указать статическую функцию-член для обратного вызова, но вы также можете сделать регулярную функцию-член, который вызывается послесловие:

Статические функции-члены не имеют доступа к но могут быть указаны как обратные вызовы, где обычно требуется обычная функция C.

class FooUser 
{ 
    // static with no access to class members, but can be specified as a callback. 
    static void MyCallback(vector<IFoo*>* foos, IAsyncResult *result) 
    { 
      MyAsyncResult *res = (MyAsyncResult*)result; 
      res->sender->MyCallback(foos, result); 
    } 

    void MyCallback(vector<IFoo*>* foos, IAsyncResult *result) 
    { 
      // handle the actual callback here 
    } 

    void init() 
    { 
     IAsyncResult *res = new MyAsyncResult(this); 
     fooUser->StartGetFoos(&foos, res); 
    } 
} 
Смежные вопросы