2013-04-09 77 views
12

我正在使用套接字編程。我只是想清除與我從 - mobileorchard.com - Chatty下載的代碼有關的疑問。雖然ř& d,我看到一個函數調用在ChatRoomViewController.m文件爲什麼我們要調用doesNotRecognizeSelector:方法?

[chatRoom broadcastChatMessage:input.text fromUser:[AppConfig getInstance].name]; 

當我在Room.m文件看到,對於上述呼叫的執行;它是

- (void)broadcastChatMessage:(NSString*)message fromUser:(NSString*)name 
{ 
    // Crude way to emulate an "abstract" class 
    [self doesNotRecognizeSelector:_cmd]; 
} 

我GOOGLE爲「doesNotRecognizeSelector:」,根據其Apple用於錯誤處理,說明「運行時系統調用只要對象接收aSelector消息時,它不能響應或轉發該方法」我的問題是,爲什麼開發者調用broadcastChatMessage:fromUser:函數,如果它沒有在那裏使用,並且處理哪個方法的「selector not found」異常?

根據Stackovrflow,其用於創建抽象類,根據此Question,其避免「不完整的實現」警告。

我仍然不明白爲什麼該方法用於那個Chatty Code,請幫助我理解爲什麼使用該方法的原因。

+1

看起來好像該應用程序的原始開發人員正試圖模擬C++抽象基類的功能,因爲它的實例無效。它只是一種更極端的形式,使方法無所作爲或返回佔位符值(通常爲0或NULL)。 – CodaFi 2013-04-09 05:43:15

回答

11

這是存在於每個NSObject派生對象上的方法,該方法在運行時調用中未識別某個方法時會觸發發生異常的路徑。例如,如果您嘗試向NSString發送郵件-foo,它將最終結束,因爲這不是NSString上的有效方法。

在這種情況下,Chatty類Room是從不直接使用的基類。 LocalRoomRemoteRoom派生自它,並且這兩個類都提供了-broadcastChatMessage:fromUser的重要實現。沒有人曾經調用過這個基類的版本,但是對於「完整性」,程序員已經保證了子程序員必須通過實現這個方法來覆蓋它,但是然後轉過身來調用它來觸發異常。

事情是,這不是特別慣用的Objective-C。 「抽象」類是C++和其他語言的概念;它的基類只是作爲子類的「模式」存在。 (在ObjC中,這通常通過在沒有意義的狀態時創建正式的@protocol來完成,因爲那裏(大部分)不在這裏)。

請注意,致電-doesNotRecognizeSelector:是任意的。在這裏沒有必要避免編譯器警告(因爲方法實際上已經實現),並且原作者可能很容易直接拋出異常,或者什麼都不做。

4

在我看來,你已經回答了你自己的問題。沒有辦法在Objective-C中創建抽象類,所以最接近的做法是讓你需要重寫拋出異常的方法。如果在子類中重寫此方法,則不再調用doesNotRecognizeSelector:。基本上這是一種讓開發人員承諾在其子類中實現此方法的方法。另外,正如你所提到的,如果你不把它放進去,那麼編譯器會發出一個警告,因爲在頭文件中定義的方法沒有實現。這將執行與不執行相同的行爲,但編譯器會意識到您正在故意這樣做。

相關問題