我正在爲可可應用程序編寫中間件,並且正在討論如何爲許多長時間運行的進程設計回調。可可回調設計:最佳實踐
當UI將調用其執行很長一段時間的函數,它需要提供一個委託,以允許至少:
- 成功(有返回值)失敗的
- 報告的報告(錯誤值)
- 進展的報告(已完成,預計總)
我已經在過去嘗試了一些技巧,下面
所示@interface MyClass {
}
//Callback Option1, delgate conforming to protocol
-(void) longRunningProcess2:(id<CallbackProtocol>) delegate;
//Callback Option2, provide a delegate and allow it to provide selectors to callback
-(void) longRunningProcess3:(id) delegate success:(SEL) s1 failure:(SEL) s2 progress:(SEL) s3
@end
對於選項1,問題是如何短語委託響應。我認爲第一種方式是(函數名稱是最小的爲簡單起見)
//have a generic callback protocol for every function
@protocol CallbackProtocolGeneric
-(void) success:(id) returnValue;
-(void) failure:(NSError*) error;
@optional
-(void) progress:(NSInteger) completed of:(NSInteger) total;
@end
//have a separate protocol for every function
@protocol CallbackProtocolWithObjectAForOperation1
-(void) objectA:(ObjectA*) objectA operation1SucceedWithValue:(ReturnObject*) value;
-(void) objectA:(ObjectA*) objectA operation1FailedWithError:(NSError*) error;
@optional
-(void) objectA:(ObjectA*) objectA operation1didProgress:(NSInteger) completed of:(NSInteger) total;
@end
以我的經驗, 回調選項1使用通用協議很難因爲使用如果一個類想成爲一個回調多個操作時,它無法區分它正在接收哪個回調。
回調選項2使用起來很麻煩,感覺不太自然。另外如果協議被擴展,則需要修改每個呼叫。
使用特定協議對於每個過程回撥選項1似乎是最可讀的和可擴展的方法,但是不知做一個新的協議爲每一個功能是太冗長(說一個給定的對象具有10+這種「長期操作」,然後是10種不同的協議)。
有其他人來執行這樣的設計時,什麼樣的結論?
--edit: 在答覆戴夫德隆的回答
我有一個具有「長作業」,每個類或類之間的操作的不真正涉及三類。一些是網絡資源請求,另一些則是長時間處理請求。
- 編輯: 一個方面,我似乎有一個問題,我不能調用具有多個參數的消息的運行循環選擇器。這是一個設計限制還是有解決方法?
例如,我有一條消息,如 - (ID)someMessage:(ID)值1 otherData:(ID)數值2 MOREDATA:(ID)VALUE3
哪個隊列runLoop的不支持這種選擇的performSelector功能。
我同意明確指定回調,儘管冗長,會導致更好的可讀性。我還沒有讀入'塊',但他們看起來比選擇器更加靈活。我總是覺得重載一個參數/兩個參數執行選擇器功能,其中一個黑客和一個糟糕的設計結果。 – Akusete 2010-07-03 07:56:17