I'm looking to implement the NSMutableCopying
interface as I have a set of objects which are immutable, but I also need to be able to create modified copies. Let's assume we've got a movie defined something like this (of course, really there would be more properties):
// BBMovie.h
@interface BBMovie : NSObject < NSCopying, NSMutableCopying >
@property(readonly, nonatomic, copy) NSString *title;
@end
@interface BBMutableMovie : BBMovie
@property(readwrite, nonatomic, copy) NSString *title;
@end
From what I've read, if you need to set the ivars outside the constructor, as I will here to implement NSCopying
, then it's good practice to define private setters for them. So I'd end up with an implementation like this for BBMovie
(note that these types are not designed to allow subclassing):
// BBMovie.m (note: compiling with ARC)
@interface BBMovie ()
@property(readwrite, nonatomic, copy) NSString *title;
@end
@implementation BBMovie
@synthesize title = _title;
- (id)copyWithZone:(NSZone *)zone
{
BBMovie *copy = [[BBMovie allocWithZone:zone] init];
if (copy) copy.title = self.title;
return copy;
}
- (id)mutableCopyWithZone:(NSZone *)zone
{
BBMutableMovie *copy = [[BBMutableMovie allocWithZone:zone] init];
if (copy) copy.title = self.title;
return copy;
}
@end
Now, given that I know the BBMovie
implementation has both getters and setters for the properties, it seems like I should be able to implement BBMutableMovie
as simply as:
@implementation BBMutableMovie
@dynamic title;
@end
Is there any problem with this approach, and/or am I missing anything?
Of course I realise that the BBMovie implementation isn't truly immutable as it will respond to the set messages if sent by consumers of the library, but that isn't really a concern to me as it doesn't present a security risk and falls outside 'normal' usage of the library.