2012-03-05 13 views
1

Iました次のコード:ブーストなしでクラスの関数としてパラメータとしてextern関数を渡す最高の安全方法?

#include <iostream> 

typedef void (*FuncPtr)(int); 

extern void MyFunc(FuncPtr callback)  

class MyClass 
{ 
public: 
    void SomeFunction(int n) 
    { 
     std::cout << "bla: " << n << std::endl; 
    } 
}; 

int main() 
{ 
    MyClass obj; 
    MyFunc(/* */); 
} 

パラメータとしてMyFunc機能で(SomeFunction)ブーストなしのクラスの関数を渡すための最良かつ安全な方法は何ですか?

+1

http://www.parashift.com/c++-faq-lite/pointers-to-members.html –

+1

'SomeFunction'を' static'として宣言してください。 。 –

+0

"メンバー関数へのポインタを関数パラメータとしてどのように渡すのですか"という質問はありますか? –

答えて

2

あなたのコンパイラがそれを許可しても、私はあなたが未定義の動作に入ることはできません。

SomeFunctionは、フリー関数のようではなく、メンバ関数です。つまり、オブジェクト上で動作するため、コンテキスト外で呼び出すことは災害への確実な道です。

2

Cコールバックのためのイディオムは、関数を通ってバックコールバックに任意のパラメータを渡すをユーザデータを含めることである。

typedef void (*FuncPtr)(int, uintptr_t user_data); 

extern void MyFunc(FuncPtr callback, uintptr_t user_data); 

使用するコールバックを使用してクラスのメソッドを呼び出します

class MyClass 
{ 
public: 
    void SomeFunction(int n) 
    { 
     std::cout << "bla: " << n << std::endl; 
    } 
private: 
    static void SomeFunctionEntry(int n, uintptr_t user_data) 
    { 
     MyClass *ths = (MyClass *) user_data; 
     ths->SomeFunction(n); 
    } 
}; 

静的関数SomeFunctionEntryがcallbaとして呼び出すことができる自由な関数である:thisポインタを渡すuser_data ck。あなたはそのuser_data引数が有効なクラスのインスタンスであることを確認:

int main() 
{ 
    MyClass obj; 
    MyFunc(&MyClass::SomeFunctionEntry, (uintptr_t) &obj); 
} 

(サイドノート:ために困難であるため、マルチスレッド環境でコールバックとしてobjのような自動変数を渡すために非常に悪い考えです

+0

+1完全な答え、さらに古典的な "非常に悪い考え"がそこにあります:) –

関連する問題