我对从方法返回的对象的内存警告感到困惑。 这是我的代码。
-(void)returnHeaderView
{
self.headerView=[[UIView alloc]init];
headerView.frame=CGRectMake(0, 0, 955, 45);
UILabel *fromLabel=[self returnLabel];
fromLabel.frame=CGRectMake(400, 5, 200, 44);
fromLabel.text=@"Open Time";
[headerView addSubview:fromLabel];
[fromLabel release];(in correct decrement of the reference count of an object that is not owned at this point by the caller)
[self.headerView addSubview:fromLabel];
[self.view addSubview:self.headerView];
[self.headerView release];
}
-(UILabel *)returnLabel
{
UILabel *label= [[UILabel alloc] init] ;
label.textColor = [UIColor blackColor];
label.font = FONT_TITLE;
label.numberOfLines=1;
label.textAlignment=UITextAlignmentLeft;
label.lineBreakMode=UILineBreakModeWordWrap;
label.backgroundColor=[UIColor clearColor];
return label;
}
这是我的两种方法。 1 .-(无效)returnHeaderView。 2 .-(UILabel *)returnLabel。
-returnLabel返回标签,方法返回的UILabel对象的引用传递给returnHeaderView方法的fromLabel UILabel对象。 然后我从Label对象发布。
但它正在发出记忆警告( 正确减少调用者此时不拥有的对象的引用计数。)
所以任何人都建议我这个代码有什么问题。 以及如何释放方法返回的对象。
感谢。
答案 0 :(得分:3)
在returnHeaderView
中你实际上没有保留fromLabel
,因此你不拥有它而不应该在那里释放它(警告“不正确地减少一个对象的引用计数此时,呼叫者不拥有“)。
最好的选择是自动发布返回的标签:return [label autorelease];
并让它一直存在,直到周围的自动释放池耗尽。请注意,这也意味着从[fromLabel release];
方法移除returnHeaderView
来电。
如果这听起来很复杂,请按照实际建议使用ARC。
答案 1 :(得分:2)
请进行小的更改并删除泄漏并自动释放self.headerView以删除其他内存泄漏警告:
-(void)returnHeaderView
{
self.headerView=[[[UIView alloc]init] autorelease];
headerView.frame=CGRectMake(0, 0, 955, 45);
UILabel *fromLabel = [[self returnLabel] retain];
fromLabel.frame = CGRectMake(400, 5, 200, 44);
fromLabel.text = @"Open Time";
[headerView addSubview:fromLabel];
[self.headerView addSubview:fromLabel];
[self.view addSubview:self.headerView];
//[self.headerView release];
}
-(UILabel *)returnLabel
{
UILabel *label= [[UILabel alloc] init] ;
label.textColor = [UIColor blackColor];
label.font = FONT_TITLE;
label.numberOfLines=1;
label.textAlignment=UITextAlignmentLeft;
label.lineBreakMode=UILineBreakModeWordWrap;
label.backgroundColor=[UIColor clearColor];
return [label autorelease];
}
答案 2 :(得分:1)
在我看来,您的returnLabel
方法返回一个保留计数为1的对象,而不是编译器建议的零。我想您可能只需要更改方法名称,以便为编译器提供有关返回对象所有权的提示。尝试将returnLabel
更改为createReturnLabel
。然后该方法将符合copy/create naming convention。
答案 3 :(得分:1)
您可以通过更改代码来避免泄漏:
-(void)returnHeaderView
{
self.headerView=[[UIView alloc]init];
headerView.frame=CGRectMake(0, 0, 955, 45);
UILabel *fromLabel = [[self returnLabel] retain];
fromLabel.frame = CGRectMake(400, 5, 200, 44);
fromLabel.text = @"Open Time";
[headerView addSubview:fromLabel];
[self.headerView addSubview:fromLabel];
[self.view addSubview:self.headerView];
[fromLabel release];
[self.headerView release];
}
-(UILabel *)returnLabel
{
UILabel *label= [[UILabel alloc] init] ;
label.textColor = [UIColor blackColor];
label.font = FONT_TITLE;
label.numberOfLines=1;
label.textAlignment=UITextAlignmentLeft;
label.lineBreakMode=UILineBreakModeWordWrap;
label.backgroundColor=[UIColor clearColor];
return [label autorelease];
}
建议:避免此类泄漏的最佳方法是使用ARC。