繁体   English   中英

在以下程序中对象的引用计数是多少?

[英]What is the reference count of an object in the following program?

1)禁用ARC。

2)我有以下代码:

- (IBAction)btnsecondClicked:(id)sender {

     NSString *myname;
     myname  = retrieveName();
}


NSString * retrieveName()
{
  NSString *tmpStr = [[NSString alloc] initWithString "StackOverFlow"];
  return tmpStr;
}

我尝试了Analyser,它说

“对象泄漏:在此执行路径中稍后将不引用分配的对象,并且保留计数为+1”

指向调用retrieName行旁边的行。

我的问题:

该对象的保留计数是多少? 不应该是2吗?

因为:

  1. 第一个引用计数在retrieveName()

    2.第二个计数在btnsecondClicked() ,其中myname变量保存在哪里?

    即: myname = retrievedName () ->它不会增加引用计数吗?

在此步骤中,您创建了字符串NSString *tmpStr = [[NSString alloc] initWithString "StackOverFlow"]; 因此,您拥有+1引用计数,因为始终alloc:返回具有+1计数的对象。 那你将在哪里发布呢? 这就是为什么它显示为泄漏。

从所有权的角度考虑-关注您想说的内容的语义,而不是实现的编写方式。 这是面向对象的编程。

谁调用alloc都会拥有一个引用。 呼叫retain任何人都retain建立所有权。 因此,每次对alloc或keep的调用都必须与一个发布相匹配-如果您希望autorelease则可以立即releaseautorelease release

堆栈结果的规范是自动发布。 这甚至体现在工厂方法(例如[NSString +string]返回这样的非所有者引用)的规则中。

不可以,因为传递对象不会增加保留计数。

但是,如果您做了

- (IBAction)btnsecondClicked:(id)sender {
   NSString *myname;
   myname  = [retrieveName() retain];
}

然后,保留计数将增加到2,因为您要明确声明对该特定对象的所有权。

- (IBAction)btnsecondClicked:(id)sender {

     NSString *myname;   // nil object, no retain count
     myname  = retrieveName(); // we received the object with retain count 1 (not 2 because you are not sending `retain` to the received object)
} // you exited the function without having global reference on the object, mynames is lost because it was created inside the function, i.e. you leaked at this step 



NSString * retrieveName()
{
  NSString *tmpStr = [[NSString alloc] initWithString "StackOverFlow"]; // retain count is 1
  return tmpStr; // tmpStr returned with retain count of 1
}

现在这里是固定的代码

- (IBAction)btnsecondClicked:(id)sender {

     NSString *myname;
     myname  = retrieveName();  // retain count = 1 and the object is the autorelease pool
}// you exited the function, autorelease pool automatically drained, the object is released, no leak



NSString * retrieveName()
{
  NSString *tmpStr = [[NSString alloc] initWithString "StackOverFlow"];
  return [tmpStr autorelease];  // the object with retain count=1, and added to releasePool
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM