2015-10-12 182 views
1

我已經編寫了一個庫,允許通過檢查收到的ASCII字符來將函數綁定到關鍵事件。它適用於主代碼中定義的非成員函數。它不適用於成員函數。我知道這是因爲成員函數和非成員函數是不同類型的。我如何將以前未定義的類的函數傳遞給我的庫中的此函數?傳遞函數和成員函數作爲另一個函數的參數

的類型定義:

typedef void (*tobind)(); 

有問題的功能:

void Keybinder::bind(char key,int mode,tobind func) { 
switch(mode){ 
    //execute depending on the event mode argument 
    case 0: 
     pressed[key] = func; //assign the function to the character pressed event 
     break; 
    case 1: 
     down[key] = func; //assing the function to the character down event 
     break; 
    case 2: 
     released[key] = func; //assign the function to the character released event 
     break; 
} 
} 
+3

也許std :: function? C和C++聲明的語法可能很糟糕,std :: function有助於這個和其他的東西。 –

+1

它比_「更進一步,因爲成員函數和非成員函數是不同類型的。」_這些類型生活在完全不同的「類」類型中。 –

+1

Google用於「成員函數綁定C++」。 –

回答

0

使用向前decleration + std::bind

template <class F, class... Args> 
    void Keybinder::bind(char key,int mode,F&& f,Args&&... args){ 
    std::function<void()> callback = std::bind(std::forward<F>(f),std::forward<Args>(args)...); 
    //use callback as original func 
} 

做通知書的,非靜態成員函數需要this指針被傳遞給它們。

struct Foo{ 
    void func(){}; 
}; 

Foo f; 
keybinder.bind('a',4,&Foo::func,&f); 
0

我如何傳遞一個以前未定義類的功能,這個功能在我的圖書館?

你不能用Keybinder::bind的現有接口做到這一點。

1

如果您使用的編譯器支持C++ 11語法,那麼我會建議使用std::functionstd::bind方法。

你的typedef是這樣的:

typedef std::function<void()> tobind; 

你會使用std ::綁定像這樣:

auto func = std::bind(&Foo, arg1, arg2); // non-member usage 
auto memFunc = std::bind(&A::MemberFoo, aInstance, arg1, arg2); // member-function usage 
0

FWIW,有點醜陋的中間解決方案 - 如果您的圖書館裝訂方法使它 - 綁定到一個函數,並將特定實例作爲引用/指針(在您的庫允許回調的任何「用戶數據」中)。 static函數能夠充當參考實例的friend,因此可以訪問其成員,就好像它們是它自己的一樣。但是,你基本上還是回到了C式的'OOP',所以這不是一個非常優雅的方式來做到這一點,如果你有更好的選擇可用。

我打算假設在我使用這種模式的時候,我使用的庫不支持任何更好的方法。 B-)

相關問題