2009-05-22 15 views
9

Ich verstehe, dass Protokolle wie Schnittstellen in anderen Sprachen sind - sie erklären erwartete Methoden - während Kategorien Ihnen erlauben, neue Methoden zu bestehenden Typen hinzuzufügen (vielleicht sogar Typen, die Sie nicht besitzen.)Warum verwendet das iPhone SDK für einige Delegierte Kategorien anstelle von Protokollen?

Warum, dann , verwendet das iPhone SDK manchmal Kategorien zum Deklarieren von Delegattypen? Normalerweise würde ich erwarten, dass alle Delegierten ID <MyDelegateProtocol> eingegeben werden, aber es gibt viele Beispiele, wo dies nicht der Fall ist.

Siehe zum Beispiel NSURLConnection. Sein Delegat ist "ID" und der "Vertrag" wird als eine Kategorie für NSObject (NSURLConnectionDelegate) deklariert.

Also: Was ist die Motivation für die Verwendung von Kategorien in diesen Fällen?

Antwort

13

In Objective-C 2.0 wurde die @optional-Protokoll-Direktive eingeführt, mit der bestimmte Protokollmethoden als optional deklariert werden können. Vor Obj-C 2.0 wurden Kategorien verwendet, um optionale Delegate-Methoden zuzulassen (speziell Kategorien für NSObject, die informelle Protokolle genannt werden).

Meine Vermutung ist, dass die meisten der Kategorie-anstelle-von-Protokoll-Verwendung im iPhone SDK ist ein Überbleibsel aus den entsprechenden Mac-Klassen. Zum Beispiel existiert NSURLConnection sowohl im Mac- als auch im iPhone-SDK, daher wird der Code wahrscheinlich geteilt. Da Apple noch nicht dazu übergegangen ist, alle Mac-Klassen zu ändern, um formale Protokolle zu verwenden, bleibt uns eine gewisse Inkonsistenz.

+0

Das war meine Vermutung, aber ich wusste es nicht sicher. Vielen Dank! –

+0

Erwarten Sie, die Änderung zu Protokollen zu sehen, kommen ziemlich bald jedoch. Da nun optionale Protokollmethoden erlaubt sind, wird der Code durch die Verwendung der Protokollmethoden ein wenig aufgeräumt und viele der jetzt unnötigen Kategorien entfernt. (Sie sind cool und alles, aber anstatt Methoden zur Laufzeit auf NSObject anzuheften, denke ich, dass die Implementierung eines Protokolls durch einen Delegierten sowohl konzeptionell als auch aus Laufzeitsicht viel sauberer ist.) –

4

Bis zur Überarbeitung von Objective-C, die mit OS X 10.5 und dem iPhone SDK namens "Objective-C 2.0" ausgerollt wurde, konnte man nur optionale Protokolle mit Kategorien erstellen. In Objective-C 2.0 wurde ein neues @optional-Schlüsselwort in Protokollen hinzugefügt, um zu markieren, welche Methoden optional waren (der Rest ist implizit erforderlich).

Also ich denke, was Sie sehen, ist ein leichter Halt von den früheren Tagen vor dem Schlüsselwort @optional.

Edit: Beantworten Sie das Follow-up, das in der ursprünglichen Frage erschien: Die Motivation für die Verwendung einer Kategorie auf NSObject/id für ein informelles Protokoll besteht teilweise zu dokumentieren und zu gruppieren, welche Methoden das Objekt in seiner Datenquelle aufrufen kann delegate oder was auch immer), und in geringerem Maße, um Compiler-Warnungen zu vermeiden, die Methoden aufrufen, die der Compiler nicht kennt, sind in dem Objekt vorhanden, das den Aufruf empfängt. Stellen Sie sich vor, Sie wären derjenige, der die Klasse implementiert, die diese Datenquellenmethoden aufruft - Sie würden wahrscheinlich überprüfen wollen, ob die Methode vorhanden ist, indem Sie [obj answerToSelector: @selector (meine: datenquelle: methode :)] verwenden, wenn Sie den my aufrufen möchten : Datenquelle: Methode: Methode für das Objekt obj.

+0

Macht Sinn - danke! –

1

Das ist ein Vermächtnis von objective-c 1.0, das keine "optionale Protokollmethode" hat.