初始化块内的对象

时间:2011-12-19 15:16:30

标签: ios xcode initialization block initializing

我正在尝试初始化一个dict变量,但我不明白为什么一种方法有效,而另一种方式则不然。

在案例1中一切正常,我可以在以后使用dict 在案例2中,它将很快被释放(它将变成一个僵尸)并且如果我稍后尝试使用它(在块之外)程序崩溃。

这是我为ios编写的一些代码(c ++与objective-c混合) 在块内部,我尝试以两种不同的方式初始化变量dict。

class Data
{
public:
    NSMutableDictionary *dict;

    void DoSomeStuff()
    {
    [NSSomeFrameworkTool doSomeStuffWithCompletionHandler:^(NSError *err) {
        // case 1 - OK
        dict = [[NSMutableDictionary alloc] initWithDictionary:[NSKeyedUnarchiver unarchiveObjectWithFile:@"dict.dat"]];

        // case 2 - will crash later if i try to use dict
        dict = [NSKeyedUnarchiver unarchiveObjectWithFile:@"dict.dat"];   }];
    }
}

该类具有类变量dict,它在DoSomeStuff()方法中初始化 该方法从ios框架调用一个方法,该方法使用块(作为回调)来通知我某些任务已完成。

我想知道为什么案例1和案例2的工作方式不同。也许禁止在块内部使用引用,这是在这个块内初始化的?
以case2中显示的方式执行此操作有什么问题?

2 个答案:

答案 0 :(得分:2)

在第一种情况下,你不会释放你的词典,在第二种情况下,它是自动释放的,所以你应该保留它。

dict = [[NSKeyedUnarchiver unarchiveObjectWithFile:@"dict.dat"] retain];

答案 1 :(得分:2)

我认为你可以在这里使用一个块变量。

__block NSMutableDictionary *dict;

变量在块内部是不可变的。它们是一个常量副本,是“块创建”时变量的快照,因此无法在块内修改它。块变量将变量从“堆栈”移动到“堆”,允许您更改其状态。我绝不是积木方面的专家,因为他们对于目标c来说相对较新。但如果你谷歌可以学习,那么有一些好的文章。

http://pragmaticstudio.com/blog/2010/7/28/ios4-blocks-1