我正在处理NSXMLParser
示例代码,我有几个关于如何设置委托和属性的问题,特别是在AppDelegate
中。
在界面中,AppDelegate
被声明为跟随NSXMLParserDelegate protocol
,但它似乎没有实现任何协议方法或在任何时候将自己设置为委托。这些似乎属于ParseOperation
类。这只是一个错字吗?
@interface SeismicXMLAppDelegate : NSObject <UIApplicationDelegate, NSXMLParserDelegate> {
UIWindow *window;
UINavigationController *navigationController;
RootViewController *rootViewController;
@private
// for downloading the xml data
NSURLConnection *earthquakeFeedConnection;
NSMutableData *earthquakeData;
NSOperationQueue *parseQueue;
}
该接口还声明了一些私有属性。这些在.m文件的接口扩展中再次定义。
@interface SeismicXMLAppDelegate ()
@property (nonatomic, retain) NSURLConnection *earthquakeFeedConnection;
@property (nonatomic, retain) NSMutableData *earthquakeData; // the data returned from the NSURLConnection
@property (nonatomic, retain) NSOperationQueue *parseQueue; // the queue that manages our NSOperation for parsing earthquake data
- (void)addEarthquakesToList:(NSArray *)earthquakes;
- (void)handleError:(NSError *)error;
@end
好吧,我想我明白这意味着其他类无法访问这些属性,在这种情况下这似乎是一件非常好的事情。这是一个谜 - 在applicationDidFinishLaunching:
的实现中,使用不同的符号定义了两个属性。
self.earthquakeFeedConnection =
[[[NSURLConnection alloc] initWithRequest:earthquakeURLRequest delegate:self] autorelease];
VS
parseQueue = [NSOperationQueue new];
为什么一个人使用self.propertyName =
而另一个人使用propertyName =
?我知道parseQueue
和earthquakeFeedConnection
最终都会将保留计数设为1,但earthquakeFeedConnection
是autorelease pool
的一部分会自动释放,而我们会自动释放由于使用parseQueue
而未调用+new
,因此必须稍后发布autorelease
。
内存考虑并不能解释自我的使用。还有其他区别吗?
答案 0 :(得分:1)
alloc
和new
返回保留一次的对象。 init
对内存管理没有任何影响,autorelease
将稍后释放该对象。
如果您编写self.myProperty = ...
,则会调用synthesized
setter,其行为与您在相应属性nonatomic, retain
中定义的行为相同。 nonatomic
表示getter和setter不是线程安全的(但很快)。 retain
表示在这种情况下,setter将释放旧对象并保留新对象。如果您编写assign
而不是retain
,则setter只会分配指针,并且不会在受影响的对象上调用release或retain。
您的示例中的目标是创建两个保留一次的对象 例1:
self.earthquakeFeedConnection = [[[NSURLConnection alloc] initWithRequest:earthquakeURLRequest delegate:self] autorelease];
例2:
parseQueue = [NSOperationQueue new];
所以最后两种情况都会产生相同的结果。你也可以写
earthquakeFeedConnection = [[NSURLConnection alloc] initWithRequest:earthquakeURLRequest delegate:self];
setter-solution看起来更复杂但有一些副作用。如果您稍后注意到在getter或setter中需要特殊行为(例如:触发其他一些方法或进行一些值检查:NSString只应包含eMail-Addresses),那么您只需要覆盖getter或setter。如果您不使用self.myProp = ...
,那么您必须搜索使用情况,并且还必须更改该代码段。
委托 - 东西:是的,你是对的:通常你必须(或应该)在接口定义中列出alle实现的协议,但NSURLConnectionDelegate
是一个例外。我不知道为什么(我在NSObject
- class-reference中找不到实现点),但每个NSObject
都已实现该委托。因此,您不必提及您的类正在实现该委托。
答案 1 :(得分:0)