在哪里发布__block变量?

dev*_* gr 4 objective-c ios

我有以下代码片段:

-(void) doSomething
{
    __block NSMutableArray *objArray = [[NSMutableArray alloc] initWithCapacity:0];
      [self performOperationWithBlock:^(void)
      {
         //adding objects to objArray
         .
         .
         //operation with objArray finished

         // 1. should objArray be released here?
      }];

      //2. should objArray be released here?
}
Run Code Online (Sandbox Code Playgroud)

我应该自动发布objArray吗?

Rui*_*res 5

如果是异步调用,则NSMutableArray在实际块内部创建是有意义的:

  [self performOperationWithBlock:^(void)
  {
     NSMutableArray *objArray = [[NSMutableArray alloc] initWithCapacity:0];

     //adding objects to objArray
     .
     .
     //operation with objArray finished

     // 1. should objArray be released here?
  }];
Run Code Online (Sandbox Code Playgroud)

因为在块之后你不需要它(它只对异步操作的持续时间有意义),所以最后在你使用它之后释放它.或者,您可以简单地:

     NSMutableArray *objArray = [NSMutableArray array];
Run Code Online (Sandbox Code Playgroud)

在这种情况下,您不需要释放它.

如果是同步调用,则应release在阻止之后进行.


注意:我假设您NSMutableArray在块上使用之前填充了,这意味着在块启动之前创建它是有意义的.

异步方法:

-(void) doSomething
{
   // Remove the `__block` qualifier, you want the block to `retain` it so it
   // can live after the `doSomething` method is destroyed
    NSMutableArray *objArray = // created with something useful

    [self performOperationWithBlock:^(void)
     {
       // You do something with the objArray, like adding new stuff to it (you are modyfing it).
       // Since you have the __block qualifier (in non-ARC it has a different meaning, than in ARC)
       // Finally, you need to be a good citizen and release it.
     }];

    // By the the time reaches this point, the block might haven been, or not executed (it's an async call).
    // With this in mind, you cannot just release the array. So you release it inside the block
    // when the work is done
}
Run Code Online (Sandbox Code Playgroud)

同步方法:

它假定您需要立即获得结果,并且在执行块之后进一步使用Array时这是有意义的,因此:

-(void) doSomething
{
   // Keep `__block` keyword, you don't want the block to `retain` as you
   // will release it after
    __block NSMutableArray *objArray = // created with something useful

    [self performOperationWithBlock:^(void)
     {
         // You do something with the objArray, like adding new stuff to it (you are modyfing it).
     }];
    // Since it's a sync call, when you reach this point, the block has been executed and you are sure
    // that at least you won't be doing anything else inside the block with Array, so it's safe to release it

    // Do something else with the array

    // Finally release it:

    [objArray release];
}
Run Code Online (Sandbox Code Playgroud)