Class extensions are like “anonymous” categories, except that the methods they declare must be implemented in the the main @implementation block for the corresponding class.
It is common for a class to have a publicly declared API and to then have additional API declared privately for use solely by the class or the framework within which the class resides. You can declare such API in a category (or in more than one category) in a private header file or implementation file as described above. This works, but the compiler cannot verify that all declared methods are implemented.
For example, the compiler will compile without error the following declarations and implementation:
@interface MyObject : NSObject |
{ |
NSNumber *number; |
} |
- (NSNumber *)number; |
@end |
@interface MyObject (Setter) |
- (void)setNumber:(NSNumber *)newNumber; |
@end |
@implementation MyObject |
- (NSNumber *)number |
{ |
return number; |
} |
@end |
Note that there is no implementation of the setNumber method. If it is invoked at runtime, this will generate an error.
Class extensions allow you to declare additional required API for a class in locations other than within the primary class @interface block, as illustrated in the following example:
@interface MyObject : NSObject |
{ |
NSNumber *number; |
} |
- (NSNumber *)number; |
@end |
@interface MyObject () |
- (void)setNumber:(NSNumber *)newNumber; |
@end |
@implementation MyObject |
- (NSNumber *)number |
{ |
return number; |
} |
- (void)setNumber(NSNumber *)newNumber |
{ |
number = newNumber; |
} |
@end |
Notice that in this case:
No name is given in the parentheses in the second @interface block;
The implementation of the setNumber method appears within the main @implementation block for the class.
The implementation of the setNumber method must appear within the main @implementation block for the class (you cannot implement it in a category). If this is not the case, the compiler will emit a warning that it cannot find a method definition for setNumber.
Last updated: 2008-02-05