Why do Objective-c protocols adopt other protocols? - objective-c

I've seen Objective-c protocols defined in the following way:
#protocol MyProtocol <SomeOtherProtocol>
// ...
#end
Why do protocols adopt other protocols? I'm especially curious why a protocol would adopt the NSObject protocol.

It is simply the same concept as inheritance for classes.
If a protocol adopt another protocol, it "inherits" the declared methods of this adopted protocol.
The NSObject protocol especially declares methods such as respondsToSelector:. So this is especially useful if you declare a #protocol that have #optional methods, because when you will then call methods on objects conforming this protocol, you will need to check if the object responds to the method before calling it if this method is optional.
#protocol SomeProtocol <NSObject>
-(void)requiredMethod;
#optional
-(void)optionalMethod;
#end
#interface SomeObject : NSObject
-(void)testMyDelegate;
#property(nonatomic, assign) id<SomeProtocol> myDelegate;
#end
#implementation SomeObject
#synthesize myDelegate
-(void)testMyDelegate {
// Here you can call requiredMethod without any checking because it is a required (non-optional) method
[self.myDelegate requiredMethod];
// But as "optionalMethod" is #optional, you have to check if myDelegate implements this method before calling it!
if ([myDelegate respondsToSelector:#selector(optionalMethod)]) {
// And only call it if it is implemented by the receiver
[myDelegate optionalMethod];
}
}
#end
You will only be able to call respondsToSelector on myDelegate if myDelegate is declared as a type that implements respondsToSelector (otherwise you will have some warnings). That's why the <SomeProtocol> protocol needs to adopt itself the <NSObject> protocol, which itself declares this method.
You may think of id<SomeProtocol> as "any object, whatever its type (id), it just has to implement the methods declared in SomeProtocol, including the methods declared in the parent protocol NSObject. So it can be an object of any type but because SomeProtocol adopts the NSObject protocol itself, it is guaranteed that you are allowed to call respondsToSelector on this object, allowing you to check if the object implements a given method before calling it if it is optional.
Note that you may also not make SomeProtocol adopt the NSObject protocol and instead declare your variable as id<SomeProtocol,NSObject> myDelegate so that you can still call respondsToSelector:. But if you do that you will need to declare all your variables this way everywhere you use this protocol... So this is much more logical to make SomeProtocol directly adopt the NSObject protocol ;)

Inheritance...................

Related

Objective C Protocols and Inheritance

Ok, there are several questions with "Protocol" and "Inheritance" but I can't really find the answer to my question. I have a class with a protocol. For example:
#class SomeClass;
#protocol SomeDelegate <NSObject>
#optional
-(void) someMethod;
#end
#interface SomeClass : NSObject
{
id<SomeDelegate> delegate;
}
#property id<SomeDelegate> delegate;
-(void) thisDoesStuff;
#end
Then I have a different class whose object will be a delegate of a SomeClass object:
#interface DiffClass: SomeClass<SomeDelegate>
// This method will conform to the one specified on the protocol
-(void) someMethod;
#end
My question is, does DiffClass inherit from SomeClass? I'm considering the syntax in Objective C for inheritance:
#interface ClassA : SuperClassOfClassA
Where, in the above, ClassA inherits from SuperClassOfClassA.
Additionally, in Objective C, is it possible to inherit from one class and adopt a protocol from a different class? I guess what I'm trying to get at is if it's possible that two objects are able to communicate to each other through delegates without having to inherit from that protocol's class (I hope I'm making sense).
Thanks in advance!
In practice, your code would be very strange.
First, you don't have a class with a protocol. You have a protocol named SomeDelegate. Then you have a class SomeClass, which is unrelated to the protocol. Well, it has an instance variable that supports SomeDelegate, but that has nothing to do with the protocol.
Then you create a class that is both a subclass of SomeClass, and supports the SomeDelegate protocol. That's unusual. I mean DiffClass both supports the protocol itself, and has a delegate supporting the protocol. That's a bit strange.
Nevertheless, DiffClass is a subclass of SomeClass, and you promised that it supports the protocol SomeDelegate, so that's fine.
But really: A protocol doesn't belong to a class. I don't know what made you think that, but you have to remove that from your brain immediately. A protocol is a totally different thing and totally independent from a class. It's a set of requirements that any class may or may not fulfil. It exists independent of any class. Because a protocol is a set of requirements, a class can support that protocol by claiming it does (adding ) and by adding the required methods.
To answer your first question, DiffClass does inherit from SomeClass as you have it written. But it doesn't need to inherit from SomeClass. I'll be a bit more thorough below.
A protocol is a declaration of methods (and properties) that a class adopts. It does not have to be related to a class, although it often is for the delegation pattern.
For example, you could have a header that just declares a protocol. Let's call the file NewProtocol.h
#protocol NewProtocol<NSObject>
#optional
- (void)newMethod;
#end
Then any class can adopt that protocol. With your example above, this could be DiffClass. You do not need to declare the methods from NewProtocol again in the class interface.
// You would need to import NewProtocol.h
// Note that this does NOT inherit from SomeClass.
#interface DiffClass : NSObject<NewProtocol>
#end
Then the implementation of DiffClass would need to provide the declared protocol methods.
#implementation DiffClass
- (void)newMethod {
// Do stuff.
}
#end
Then SomeClass could have a property for the declared protocol above.
#interface SomeClass : NSObject
// Often you will want weak for delegates as they can cause retain cycles otherwise.
#property(nonatomic, weak) id<NewProtocol> thingThatImplementsNewProtocol;
-(void) thisDoesStuff;
#end
DiffClass does now NOT inherit from SomeClass but can be used to communicate with SomeClass. You could declare a second protocol that SomeClass adopts and a property on DiffClass to have two way communication.
Often the protocol are declared in the same header file as a class for simplicity because they are intended as delegates for specific objects.
Answer to the question 1: with the statement
#interface DiffClass: SomeClass<SomeDelegate>
The DiffClass inherits from SomeClass and also conforms the protocol(interface) SomeDelegate.
Answer to the question 2: In Objc you can inherit only from one parent class (multiple inheritance wont be supported) but you can conform as many as protocols (interfaces) you want.
Lets take and example of an drawing App. Shape is a parent class and RectangleShape, LineSahpe, TextShape, CircleShape are the children from Shape class. All four children are inheriting from their parent Shape. But you need to move the shape except LineShape. There you can have protocol (interface) as Movable. That you can do so.
#protocol Movable <NSObject>
#end
#interface Shape : NSObject
#end
#interface RectangleShape : Shape <Movable>
#end
#interface LineSahpe : Shape // cannot be moved, just for an example.
#end
#interface TextShape : Shape <Movable>
#end
#interface CircleShape : Shape <Movable>
#end
You can have a method for the protocol like this to move all Shaped which are conforming Movable protocol (interface).
- (void)move:(id <Movable>)movableShape {
}
You can implement a communication instead of moving shapes. Protocols are really useful during advanced programming.
Hope it will help you... please feedback me.

How to create a delegator in objective C?

I am trying to learn, how to implement delegation pattern in objective C. But the discussion almost exclusively concentrates on the adoption of protocols and then implementing the delegate methods that come with particular protocol - or - the delegation principle alone - or protocols alone.
What I am unable to find, is a easy to understand material about how to write a class that will serve as a delegator. By that I mean the class, which the message of some event will come from and which will provide the protocol for receiving that message - kind of 2in1 description. (protocols and delegation).
For the purpose of my learning, I'd like to go along the following trivial example, using an iPhone, a Cocoa touch application and Xcode4.2, using ARC, no Storyboard or NIBs.
Let's have a class with name "Delegator", which is a subclass of NSObject. The Delegator class has NSString instance variable named "report" and adopts the UIAccelerometerDelegate protocol.In the Delegator implementation, I will implement the the delegate method
-(void)accelerometer:(UIAccelerometer *)accelerometer didAccelerate:(UIAcceleration *)acceleration
This delegate method will create a NSString #"myReport" and store it in the report variable anytime there is an accelerometer event. Further, I want to have a second class named ReportsStorage (a subclass of NSobject), which can store some Nsstring (report) in its instance variable called latestReport.
So far so good.
Now lets get back to theDelegator Class. I'd like to implement a protocol in Delegator named ReportsDelegate which will notify the class that adopts it (the ReportsStorage class), that a report was generated and will pass this report through the delegate method, which should be (I believe) something like this
-(void)delegator:(Delegator *)delegator didCreateNewReport:(NSString *)report;
Can you please provide the code for Delegator Class (incl. the "delegate" property), that will achieve this, with a description what each line of code means?
Thanks in advance, EarlGrey
You'll need to declare the delegate property as an id<ReportsDelegate> type. That is, any object type (id) conforming to the ReportsDelegate protocol (<ReportsDelegate>). Then, if the delegate method is considered optional, check if the delegate responds to that selector before calling it. (respondsToSelector:).
Like so:
Delegator.h
#import <Foundation/Foundation.h>
// Provide a forward declaration of the "Delegator" class, so that we can use
// the class name in the protocol declaration.
#class Delegator;
// Declare a new protocol named ReportsDelegate, with a single optional method.
// This protocol conforms to the <NSObject> protocol
#protocol ReportsDelegate <NSObject>
#optional
-(void)delegator:(Delegator *)delegator didCreateNewReport:(NSString *)report;
#end
// Declare the actual Delegator class, which has a single property called 'delegate'
// The 'delegate' property is of any object type, so long as it conforms to the
// 'ReportsDelegate' protocol
#interface Delegator : NSObject
#property (weak) id<ReportsDelegate> delegate;
#end
Delegator.m
#import "Delegator.h"
#implementation Delegator
#synthesize delegate;
// Override -init, etc. as needed here.
- (void)generateNewReportWithData:(NSDictionary *)someData {
// Obviously, your report generation is likely more complex than this.
// But for purposes of an example, this works.
NSString *theNewReport = [someData description];
// Since our delegate method is declared as optional, check whether the delegate
// implements it before blindly calling the method.
if ([self.delegate respondsToSelector:#selector(delegator:didCreateNewReport:)]) {
[self.delegate delegator:self didCreateNewReport:theNewReport];
}
}
#end

Does Objective-C have something like C++ virtual functions?

In objective-c it is possible to add a #dynamic to a property.
Is this also possible for normal instance methods?
EDIT
I think i wasn't clear enough.
I want to do the following:
#interface MyClass
#property (retain) NSObject *somePropertyObject;
- (void) myMethod;
#end
#implementation MyClass
#dynamic somePropertyObject;
//Make myMethod dynamic. I do not want to implement it. Like C++ Virtual
#end
If you mean "How can I declare a method, but not provide a definition which I will subsequently provide at runtime?" Then it's easy, just use a category. Like this:
#interface MyObject : NSObject
// Methods I'll define
- (void)doFoo;
#end
#interface MyObject (DynamicallyProvidedMethods)
// Methods I won't
- (void)myDynamicMethod;
#end
#implementation MyObject
// Methods I'll define
- (void)doFoo
{
}
#end
The compiler will not complain, however if you call -myDynamicMethod at runtime, unless you have provided an implementation for it somehow, it will crash with "unrecognized selector." You can, of course, test for that at runtime by calling respondsToSelector:.
Relatedly, if you're looking to do a near-equivalent of a base class pure virtual method, I would recommend providing an empty implementation that asserts when called if it has not been overridden by a subclass. You can do that like so:
NSAssert((class_getInstanceMethod([self class], _cmd) == class_getInstanceMethod([MyObject class], _cmd)),
#"Subclass of %# must override -%#",
NSStringFromClass([MyObject class]),
NSStringFromSelector(_cmd));
// ...where overridesSelector:ofBaseClass: looks like:
//
// return ;
Of course, that won't alert you to problems at compile time, but it's better than nothing.
HTH
I think you might be asking how to declare a method that will be implemented some time later somewhere else.
The Objective-C way to do that is to use Protocols.
You declare a protocol like this, usually in a header file
#protocol MyProtocol <NSObject> {
#optional
- (void)optionalMethod;
#required
- (void)requiredMethod;
}
#end
This declares two methods, one which is optional and one is required. To use this protocol you declare the conformance when declaring the class that will implement the protocol
#interface MyConformingClass : NSObject <MyProtocol> {
}
// you don't have to redeclare methods that are declared in the protocol
#end
This new class is checked at compile time for the implementation of requiredMethod so it has to implement it, but it can choose whether or not to implement the optionalMethod
Now, any class that requires instances of objects to conform to the protocol can declare this, for example, in the interface
#interface RequiringClass : NSObject {
MyConformingClass <MyProtocol> *conformingClassObject;
}
…
#end
Again, this is checked at compile time
To make sure that the conforming class implement the #optional methods, we can use this handy structure
if [conformingClassObject respondsToSelector:#selector(optionalMethod)] {
[conformingClassObject optionalMethod];
} else {
// Do something here because the optional method isn't provided
}
Examples of this are all over Cocoa - it's a class can provide a list of actions that it would like to farm out to it's delegate, the delegate adopts the protocol and provides the implementations of those delegate methods. The calling object can then check if this delegate responds to those methods at runtime as I've described above, and call those methods to perform actions, or provide information where ever it needs to.
This is used quite a lot in Objective-C, where classes provide a list of methods that they would like some other class to perform, unlike virtual functions, where a class declares functions it wants subclasses to provide implementations for. Particularly as Composition is favoured over inheritance in the language. Rather than create a subclass to provide an implementation, you just create another class that can do the same thing, and add a reference to that in the class instead.
No.
#dynamic is just an instruction to the compiler that says: "Don't bother generating accessors for this property, I'm going to provide my own."
Using #dynamic with other methods wouldn't be helpful because the compiler doesn't generate any methods other than accessors for you, and of course you're supplying the other methods anyway.
What are you trying to accomplish?

Syntax for multiple protocols

What is the Objective-C syntax for multiple protocols?
Could you please elaborate on your question? Otherwise this is the proper way to declare a class that conforms to multiple protocols. You specify the protocols a class conforms to after the superclass declaration in a classes header file.
#interface MyClass : MySuperClass <Delegate1, Delegate2, Delegate3> {
//instance variables
}
//properties
//methods
You can achieve multiple protocols in two ways:
Method 1
#protocol p1 <NSObject>
-(void)M1
-(void)M2
#end
#protocol p2 <NSObject>
-(void)M3
-(void)M4
#end
#interface MyViewController () <p1,p2>
Method 2
#protocol p1 <NSObject>
-(void)M1
-(void)M2
#end
#protocol p2 <NSObject,p1>
-(void)M3
-(void)M4
#end
#interface MyViewController () <p1>
For an object to have multiple delegates (as opposed to being a delegate for multiple objects or classes):
The object delegating would have to
have an NSArray of delegate instance
variables.
The setDelegate setter method would
then have to add a delegate object
to this array instead of just
assigning it to one instance
variable.
The send-to-delegate code would have
to loop through the delegate
NSArray, instead of checking for
just one delegate instance variable
to be non-nil, before checking for
message handling and calling out
with the message.
Nothing much would change in all the objects or the class asking for delegation to itself.
Yes, I guess the question of comfort to multi protocols is something like the following:
#interface MyViewController () <protocol1, protocol2, protocol3>

Objective C - How can I create an interface?

I need to be able to create an interface like you create in C# to enforce a group of classes to implement certain methods.
Is this possible in objective c?
You can create a protocol. it would look something like this:
in MyProtocol.h:
#protocol MyProtocol
-(void)myMethod;
-(void)myMethod2;
#end
in MyClass.h
#import "MyProtocol.h"
#interface MyClass : NSObject<MyProtocol>
#end
If you want to receive objects of a given protocol, you can do so like this:
id<MyProtocol> var;
or
NSObject<MyProtocol> *var;
more info here
You declare a "protocol" (Objective-C's interfaces) using
#protocol MyProtocol <BaseProtocol1,...,BaseProtocolN>
//methods and properties
#end
where <BaseProtocol> is optional and indicates that MyProtocol "inherits" BaseProtocol's interface. The NSObject protocol is useful in this context because it allows you to use
#protocol MyProtocol <NSObject>
//...
#end
to indicate (when appropriate) that conforming instances of MyProtocol have the standard NSObject methods as well (e.g. -retain/-release, etc.).
You then declare that a class "conforms" to a protocol:
#interface MyClass : NSObject <MyProtocol,...,OtherProtocols>
{}
#end
And you can test whether an instance conforms to a protocol:
id myInstance = ...; //some object instance
if([myInstance conformsToProtocol:#protocol(MyProtocol)]) {
// myInstance conforms to MyProtocol
}
You can further silence compiler warnings by declaring that a variable holds instances that conform to a protocol (note that Objective-C's dynamic nature prevents the compiler from verifying that contract and you can still get runtime errors by assigning a non-conforming instance to the variable):
id<MyProtocol> o;
In this case, the compiler will complain if you send [o retain] without MyProtocol conforming to the NSObject protocol. You can silence these warnings by declaring MyProtocol as conforming to NSObject as described above or by delcaring o as
NSObject<MyProtocol> o;
Since NSObject is not the only root object in Cocoa (i.e. NSProxy does not inherit from NSObject), it's not necessarily true that all instances conforming to MyProtocol also conform to NSObject. If you know that they do, you can declare MyProtocol as conforming to NSObject.
In the Objective-C world, interfaces are called "Protocols"
According to Apple,
Protocols declare methods that can be implemented by any class. Protocols are useful in at least three situations:
To declare methods that others are expected to implement
To declare the interface to an object while concealing its class
To capture similarities among classes that are not hierarchically related
So, to declare a protocol you can:
#protocol SomeClassProtocol
- (void) do:(int) number something:(id) sender;
- (void) somethingElse;
#end
To implement a protocol , you do:
#interface MyClass : NSObject <Protocol1, Protocol2, ..., ProtocolN>
#end
Check out this link for the official documentation.
Interfaces are called protocols in Objective C
If you go to add a class to your project you will have an option to create it as protocol and you will end up with something like:
#protocol MyProtocol
-(void) DoSomething;
#end