"Protocols" are, along with categories
(see my writeup under Category
), how Objective C
s and how it gets around the fact it does not
have multiple inheritance
. Protocols and categories encompass one of the more visible bits of Objective C's Smalltalk
heritage, and are taken together really rather similar to a more nimble (in my opinion, anyway) equivalent of the interface
") capability in java
. Protocols greatly simplify certain odd issues of class structure and polymorphism
that are very clumsy to deal with.
Basically all a protocol does is group classes by functionality; a protocol prototypes a certain number of methods, and if a class adopts a protocol it is agreeing to implement every single one of the methods specified in the protocol. The class can then be described by the type of the protocol, and in general can be treated as if the protocol was a class it had inherited from.
If we were going to create a protocol named DemoProtocol, the syntax would look like this:
HypotheticalClass wanted to adopt DemoProtocol, all it would have to do is add it to the end of its @implementation
line surrounded by <html brackets>, for example changing @implementation HypotheticalClass
to @implementation HypotheticalClass <DemoProtocol>
can adopt protocols, and protocol
s can adopt other protocols, in the same way. Any of these can adopt multiple protocols, by listing multiple protocols between the <> brackets separated by commas. If a class has adopted DemoProtocol by any of these means, it *must* implement methods named thing1 and thing2. Any class that has adopted DemoProtocol, however, can be passed in methods and functions as (DemoProtocol *), and the type checking
system will be fine with that.
Protocols let you abstractly describe a functionality that could be implemented by a variety of classes in different ways; for example, NeXTStep has a protocol for event handlers. Without protocols, either all event handlers would have to be subclasses of NSEventHandler, which would be unrealistic and restrictive, or the event handling functions of NeXTStep would have to simply assume any id passed to it supports the event handling methods, without the benefit of compile-time type checking etc.
The @protocol @-directive can be used in three ways: to declare a protocol, as outlined above; to alert the compiler to the existence of a protocol defined in another file, the same way the @class directive works (see my writeup under @); and to return a protocol object (Every protocol has a corresponding instance variable of class Protocol; you can say @protocol( DemoProtocol ) somewhere in your code, and it will return a pointer to the protocol instance variable corresponding to DemoProtocol. There are defined in NSObject both class method and instance methods named conformsToProtocol(Protocol *)aProtocol; you send this message to any object, and it returns a BOOL stating whether the object adopts aProtocol, which you find the value of by using the @protocol() directive.
The language-imposed protocols i have just described are often called "Formal Protocols"; there is also something called an Informal Protocol (see the node).