无法将此代码段转换为Objective C - ARC

时间:2012-06-05 22:53:56

标签: objective-c ios automatic-ref-counting

当我想在这样的按钮中调用警报时,我有一个方便的课程:

- (IBAction)test:(id)sender {
    [MyAlertView showWithTitle:@"test" withCallBackBlock:^(int value){
        NSLog(@"Button Pressed %i", value); 
    }];
}

课程非常简单:

    @implementation MyAlertView
@synthesize callBackBlock = _callBackBlock, internalCallBackBlock = _internalCallBackBlock;

-(void)showWithTitle:(NSString *)title withCallBackBlock:(CallBackBlock )callBackBlock internalCallBackBlock:(CallBackBlock )internalCallBackBlock{
    self.callBackBlock = callBackBlock;
    self.internalCallBackBlock = internalCallBackBlock;

    dispatch_async(dispatch_get_main_queue(), ^{
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:title message:title delegate:self cancelButtonTitle:@"Cancel" otherButtonTitles:@"OK" , nil];
        [alertView show];
        [alertView autorelease];
    });

}

- (void)alertView:(UIAlertView *)alertView clickedButtonAtIndex:(NSInteger)buttonIndex{
    if (_callBackBlock) {
        _callBackBlock(buttonIndex);
    }

    if (_internalCallBackBlock) {
        _internalCallBackBlock(buttonIndex);
    }
}


-(void)dealloc{
    Block_release(_callBackBlock);
    Block_release(_internalCallBackBlock);
    [super dealloc];
}


+(void)showWithTitle:(NSString *)title withCallBackBlock:(CallBackBlock )callBackBlock{
    __block MyAlertView *alert = [[MyAlertView alloc]init];
    [alert showWithTitle:title withCallBackBlock:callBackBlock internalCallBackBlock:^(int value){
        [alert autorelease];
    }];

}
@end

我在模拟器上对它进行了分析,它没有泄漏,没有僵尸。 现在,当我换成ARC时, 每次单击测试按钮时程序都会崩溃,即使我将所有内容都引用为强大的。我猜那是因为我没有按住alertView变量。

如何用ARC做一个像这样的便利课?

追加.h文件:

#import <Foundation/Foundation.h>

typedef void(^CallBackBlock)(int value);

@interface MyAlertView : NSObject<UIAlertViewDelegate>


@property (copy) CallBackBlock callBackBlock, internalCallBackBlock;

+(void)showWithTitle:(NSString *)title withCallBackBlock:(CallBackBlock )callBackBlock;
@end

1 个答案:

答案 0 :(得分:0)

你是对的:问题在于UIAlertView创建了 showWithTitle:withCallBackBlock:internalCallBackBlock:internalCallBackBlock未被保留。

诀窍是存储在MyAlertView的实例变量中。因此,在MyAlertView.m中,添加以下内容:

@interface MyAlertView()
    @property(strong) UIAlertView *alertView;
@end

@implementation MyAlertView

@synthesize alertView;

...

并使用它来存储您在UIAlertView中创建的showWithTitle:withCallBackBlock:internalCallBackBlock:internalCallBackBlock

dispatch_async(dispatch_get_main_queue(), ^{
    self.alertView = [[UIAlertView alloc] initWithTitle:title message:title delegate:self cancelButtonTitle:@"Cancel" otherButtonTitles:@"OK" , nil];
    [self.alertView show];
});

P.S。这将是非常迂腐的,但MyAlertView实际上并不是一个视图,所以你可能想要重命名它。