我試圖將實例變量和屬性添加到現有類。我想要這樣做來擴展開源庫的基類,而不修改源代碼(爲了更容易的代碼管理)。使用類擴展將ivar和屬性添加到類
不同於常規類,一類擴展可以添加自己的 屬性和實例變量的類。如果您在類擴展中聲明 屬性,編譯器將自動合成 合成主類實現內的相關訪問器方法以及實例 變量。
我試圖在測試應用程序中做到這一點。我有一個空類ClassA
:
ClassA.h
#import <Foundation/Foundation.h>
@interface ClassA : NSObject
@end
ClassA.m
#import "ClassA.h"
@implementation ClassA
@end
然後,我添加的擴展:
ClassA的+ Ext.h
#import "ClassA.h"
@interface ClassA()
@property (nonatomic) NSString *name; // <-- this is my new property
@end
最後,在我的AppDelegate
我只是一個初始化和ClassA
嘗試設置,然後再登錄該name
。
#import "AppDelegate.h"
#import "ClassA.h"
#import "ClassA+Ext.h"
@implementation AppDelegate
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification
{
ClassA *a = [[ClassA alloc] init];
a.name = @"test";
NSLog(@"Name: %@", a.name);
}
@end
這編譯和運行,但我得到了控制檯上的錯誤:
2013-05-10 00:58:08.598 Test[53161:303] -[ClassA setName:]: unrecognized selector
sent to instance 0x108a1a630
2013-05-10 00:58:08.600 Test[53161:303] -[ClassA setName:]: unrecognized selector
sent to instance 0x108a1a630
名稱沒有登錄。如果我設置了一個斷點並檢查ClassA
實例,它沒有name
伊娃。我究竟做錯了什麼?這實際上不可能做到嗎?
這個錯誤與一個ivar在那裏或沒有沒有關係。問題在於該屬性的setter方法無法識別。註釋掉'a.name = ...'這一行並查看在日誌語句中是否存在與「getter」有關的問題。 – rmaddy 2013-05-09 23:04:35
如果我這樣做,我得到的錯誤爲getter [[ClassA name]] – DrummerB 2013-05-09 23:07:44
正如刪除的答案所述,添加到類擴展中的屬性對於類是私有的。這就是爲什麼另一個類無法看到private屬性'name'的setter或getter。 – rmaddy 2013-05-09 23:11:12