Is there a template for overriding a property?

Objective-C runtime stores a list of declared properties as metadata with the class object. Metadata includes name, type, and property attributes. The runtime library also provides several functions for extracting this information. This means that the declared property is larger than a pair of accessor methods (getter / setter). My first question is: Why do we (or the runtime) need metadata?

As you know, a declared property cannot be redefined in subclasses (except for readwrite vs. readonly). But I have a script that guarantees:

@interface MyClass : MySuperClass <NSCopying, NSMutableCopying>

@property (nonatomic, copy, readonly) NSString *string;

- (id)initWithString:(NSString *)aString;

@end


@interface MyMutableClass : MyClass

@property (nonatomic, strong, readwrite) NSMutableString *string;

- (id)initWithString:(NSString *)aString;

@end

Of course, the compiler does not skip the above code. My solution is to substitute the declared property with a pair of access methods (read-only only):

@interface MyClass : MySuperClass <NSCopying, NSMutableCopying> {
    NSString *_string;
}

- (id)initWithString:(NSString *)aString;

- (NSString *)string;

@end


@implementation MyClass

- (id)initWithString:(NSString *)aString {
    self = [super init...];
    if (self) {
        _string = [aString copy];
    }
    return self;
}

- (NSString *)string {
    return _string;
}

- (id)copyWithZone:(NSZone *)zone {
    return self;
}

- (id)mutableCopyWithZone:(NSZone *)zone {
    return [[MyMutableClass alloc] initWithString:self.string];
}

@end


@interface MyMutableClass : MyClass

- (id)initWithString:(NSString *)aString;

- (NSMutableString *)string;
- (void)setString:(NSMutableString *)aMutableString;

- (void)didMutateString;

@end


@implementation MyMutableClass

- (id)initWithString:(NSString *)aString {
    self = [super init...];
    if (self) {
        _string = [aString mutableCopy];
    }
    return self;
}

- (NSMutableString *)string {
    return (NSMutableString *)_string;
}

- (void)setString:(NSMutableString *)aMutableString {
    _string = aMutableString;

    // Inform other parts that `string` has been changed (as a whole).
    // ...
}

- (void)didMutateString {
    // The content of `string` has been changed through the interface of
    // NSMutableString, beneath the accessor method.
    // ...
}

- (id)copyWithZone:(NSZone *)zone {
    return [[MyClass alloc] initWithString:self.string];
}

@end

string , . , . , , . . . : ? ?

:

@interface MyClass : MySuperClass <NSCopying, NSMutableCopying> {
    NSString *_string;
}

@property (nonatomic, copy, readonly) NSString *string;

- (id)initWithString:(NSString *)aString;

@end


@interface MyMutableClass: MyClass

- (id)initWithString:(NSString *)aString;

- (NSMutableString *)string;
- (void)setString:(NSMutableString *)aMutableString;

- (void)didMutateString;

@end

, , myMutableObject.string, , . [myMutableObject string]. , , , , . : getter/setter , ?

+5
1

. @interface Objective-C API, , . NSString* copy NSMutableString*, , .

, , copy NSString* , , NSMutableString* ( , NSXMLElement). , .

NSMutableString, :

  • NSMutableString* string -mutableString
  • -setString: NSMutableString
  • -string,
  • , ivar NSMutableString . , , ,

, , , , .

, , API .

+3

All Articles