Objective-C 分類無法直接添加實例變量,但通過運行時關聯對象機制,可實現「偽屬性」完整語義(含 getter/setter、內存管理語義)。本文給出標準實現模板與核心要點。
#import// 唯一鍵值,通常用靜態變量地址保證唯一性 static const void *URLStringKey = &URLStringKey; @interface MyClass (CategoryName) @property (nonatomic, copy) NSString *urlStr; @end @implementation MyClass (CategoryName) - (void)setUrlStr:(NSString *)urlStr { objc_setAssociatedObject(self, URLStringKey, urlStr, OBJC_ASSOCIATION_COPY_NONATOMIC); } - (NSString *)urlStr { return objc_getAssociatedObject(self, URLStringKey); } @end
static const void *Key = &Key;,地址唯一且不污染符號表。OBJC_ASSOCIATION_COPY_NONATOMIC 對應 copy / nonatomic;其他可選 RETAIN、ASSIGN 及 ATOMIC 變體。dealloc 自動釋放,無需手動清理。AssociationsManager)映射實現。// 只讀屬性僅實現 getter
- (NSInteger)readOnlyValue {
return [objc_getAssociatedObject(self, &ReadOnlyKey) integerValue];
}
// 自定義 setter 邏輯(如觸發通知)
- (void)setCustomValue:(id)value {
id old = objc_getAssociatedObject(self, &CustomKey);
if (old != value) {
objc_setAssociatedObject(self, &CustomKey, value, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
[self customValueDidChange];
}
}
dealloc 中訪問關聯對象(已釋放)。OBJC_ASSOCIATION_ASSIGN 不持有引用,需自行保證對象生命週期,類似 weak 但不置 nil。