我想知道经验丰富的Objective-C程序员的代码有多糟糕。
self.request = [[ASIHTTPRequest alloc] initWithURL:url];
[self.request release];
这绝对不那么冗长
ASIHTTPRequest *tmp = [[[ASIHTTPRequest alloc] initWithURL:url];
self.request = tmp;
[tmp release];
但我不确定它是否足够有意义或不会导致错误。
您怎么看?
更新 我不想使用自动回收池,因为我的应用程序将在内存有限的iphone上运行。
答案 0 :(得分:2)
更新:我不想使用自动回收池,因为我的应用程序将在内存有限的iphone上运行。
请使用自动释放池!可可触摸框架本身使用它们;自己制作一个或两个autorelease
'ed对象不会改变大局。
苹果公司警告你不要对iPhone上的自动释放池上的过度依赖,比如在事件发送结束后池被耗尽之前放置对象的hundreads,但过度回避自动释放池的em也适得其反!
没有什么是黑白的;必杀技属于middle way。
答案 1 :(得分:1)
绝对选择后者,但选择更具描述性的名称而不是tmp
。您有责任发布tmp
,但您不负责发布self.request
,至少不是在给定的上下文中。
或者,如果您不介意向自动释放池中添加内容,只需执行以下操作:
self.request = [[[ASIHTTPRequest alloc] initWithURL:url] autorelease];
或
self.request = [ASIHTTPRequest requestWithURL:url];
答案 2 :(得分:1)
为什么不呢?
self.request = [[[ASIHTTPRequest alloc] initWithURL:url] autorelease];
或者,如果这是您编写或拥有源的类,则创建一个基本相同的新类方法(不是实例)(假设NSURL *
参数):
+ (ASIHTTPRequest *) requestWithURL:(NSURL *)url
{
return [[[self alloc] initWithURL:url] autorelease];
}
答案 3 :(得分:0)
您错过的不是详细程度的差异,而是内存管理方面的差异。
您经常会看到如下代码:
ASIHTTPRequest * requestTmp = [[[ASIHTTPRequest alloc] initWithURL:url];
self.request = requestTmp;
[requestTmp release];
如果保留属性并在setter方法中释放旧属性,您应该考虑发生了什么。
request
,refcount为1。 self.request = request
,现在如果setRequest
看起来像:
- (void)setRequest:(ASIHTTPRequest*)aReq
{
[aReq retain];
[request release];
request = aReq;
}
这意味着该对象保留了您传入的requestTmp
并释放了旧对象。 #{1}}的引用现在为2。
在此次通话后,您可以释放您创建的原始requestTmp
,并且您是安全的,因为保留requestTmp
的对象 - 引用计数仍为1.
但是如果你这样做:
requestTmp
您最终会释放对象self.request = [[ASIHTTPRequest alloc] initWithURL:url];
[self.request release];
供其使用的request
。请注意,您是发布对象的内部retained
,在原始情况下,您释放了request
,但该对象保留了它自己的保留引用。
所以结果与原始代码不同。