obj-c弱块中的自我:为什么第二个在两个相似的情况下不需要弱自我

时间:2013-07-28 17:18:43

标签: objective-c automatic-ref-counting objective-c-blocks retain-cycle

我终于发现我的内存错误是由于在一个块中强烈引用自我造成的。但我不知道为什么在类似的情况下,不需要弱者:

我有一个CameraCaptureManager类执行图像捕获任务,而CameraViewController具有此管理器的强大属性。管理器具有指向控制器的弱委托属性。

这是我必须在管理器中使用weakSelf的地方,否则 - (void)dealloc将不会被调用:

    // in CameraCaptureManager
    __weak CameraCaptureManager *weakSelf = self;
    void (^deviceOrientationDidChangeBlock)(NSNotification *) = ^(NSNotification *notification) {
        UIDeviceOrientation deviceOrientation = [[UIDevice currentDevice] orientation];
        [weakSelf updateVideoOrientation:deviceOrientation];
    };
    self.deviceOrientationDidChangeObserver = [notificationCenter addObserverForName:UIDeviceOrientationDidChangeNotification
                                                                              object:nil
                                                                               queue:nil
                                                                          usingBlock:deviceOrientationDidChangeBlock];  

管理器强烈保存deviceOrientationDidChangeObserver,因此需要weakSelf来打破内存保留周期。那很好,我知道了......但是我觉得我在同一个班级的类似案例中没有使用weakSelf:

[self.stillImageOutput captureStillImageAsynchronouslyFromConnection:captureConnection
                                                   completionHandler:^(CMSampleBufferRef imageDataSampleBuffer, NSError *error){

                                                       UIImage *image = nil;

                                                       if (imageDataSampleBuffer != NULL) {
                                                           NSData *imageData = [AVCaptureStillImageOutput jpegStillImageNSDataRepresentation:imageDataSampleBuffer]; 
                                                           image = [[UIImage alloc] initWithData:imageData];
                                                       } 

                                                       if ([self.delegate respondsToSelector:@selector(captureManager:capturedStillImage:)]) {
                                                           [self.delegate captureManager:weakSelf capturedStillImage:image];
                                                       }
                                                   }]; 

管理员还强烈地持有stillImageOutput,但为什么我可以在完成块中使用强大的“self”?管理器对象在块内获得dealloc与这个强大的self。我很困惑,请说清楚。

即使它不会导致任何保留周期,我还需要在第二种情况下使用weakSelf吗?

1 个答案:

答案 0 :(得分:4)

在第二个代码示例中,您有临时保留周期。当调用completionHandler块时,块被释放,并且随之捕获self,所以 发布周期被打破了。