2017-02-14 57 views
1

我已經讀了上Objective-C的塊(例如在Apple documentationa blog post,並onetwothree堆棧溢出的答案)。我想將C/C++樣式的回調傳遞給Objective-C方法。「鑄造」 C回調Objective-C的塊

這裏是我的C/C++方報關

#ifdef __cplusplus 
extern "C" { 
#endif 

    typedef void (*CALCULATION_CALLBACK)(int x); 
    void setCubeCallback(int x, CALCULATION_CALLBACK callback); 

#ifdef __cplusplus 
} 
#endif 

,並在Objective-C

@interface IOSPluginTest : NSObject 

typedef void (^CalculationHandler)(int x); 
-(void)cubeThisNumber:(int)number andCallbackOn:(CalculationHandler)callback; 

@end 

這是Objective-C的實施

#import "IOSPluginTest.h" 

@implementation IOSPluginTest 

-(void)cubeThisNumber:(int)number andCallbackOn:(CalculationHandler)callback { 
    int result = number * number * number; 
    if (callback != nil) { 
     callback(result); 
    } 
} 

@end 

出問題在最後一位中,C/C++實現

void setCubeCallback(int x, CALCULATION_CALLBACK callback) { 
    [[[IOSPluginTest alloc] init] cubeThisNumber:x andCallbackOn:callback]; 
} 

其失敗,錯誤

發送 'CALCULATION_CALLBACK'(又名 '空隙(*)(INT)'),以不兼容的類型的參數來編譯 'CalculationHandler'(又名「空隙(^) (int)')

這兩種類型的描述void(*)(int)void(^)(int),看起來和我很相似;我錯過了什麼?

+0

可能重複http://stackoverflow.com/questions/13913627/converting-a-function-pointer-to-a - 嵌段 - 在-目標c – Sulthan

回答

3

恩,「[類型]看起來非常相似」在編程中不算太多。

你缺少的是塊和函數指針是不同類型的東西。

函數指針幾乎就是函數代碼第一條指令的地址。

塊是一個對象。該對象所持有的數據中有一個函數指針,但它也有其他數據。除了作爲對象的基本基礎結構之外(例如isa指針),塊可以從其定義站點捕獲變量值。

你可以在Objective-C中使用函數指針。如果您希望兩個接口直接兼容,則只需使用CALCULATION_CALLBACK作爲Objective-C方法中參數callback的類型。

或者,你可以用函數指針的塊,像這樣:

void setCubeCallback(int x, CALCULATION_CALLBACK callback) { 
    [[[IOSPluginTest alloc] init] cubeThisNumber:x andCallbackOn:^(int result){ callback(result); }]; 
} 
1

void(*)(int)是一個方法指針void(^)(int)一個塊,在其他語言中稱爲閉包。他們根本不同。雖然方法指針只是做到這一點 - 指向一種方法,但塊也通過封裝來承載數據。這些事情是非常不同的,試圖將它們從一個方向轉換到另一個方向是沒有意義的。

但是你可以在Objective-C中使用C方法指針。