Objective-C ARC指针所有权与C ++

时间:2013-08-31 18:45:53

标签: c++ objective-c memory-management automatic-ref-counting

假设我有一个高级类来实例化一个对象,然后将它传递给一个较低级别的类:

- (void) doSomeStuff {
    MyBusinessObject* obj = [[MyBusinessObject alloc] init];
    [obj setFoo:@"bar"];
    [dataManager takeObj:obj withKey:@"abc" andKey:@"def"];
}

然后在takeObj的实现中我想保留两个不同的词典......

- (void) takeObj:(MyBusinessObject*)obj withKey:(NSString*)key1 andKey:(NSString*)key2 {
    [primaryDict setObject:obj forKey:key1];
    [secondaryDict setObject:obj forKey:key2];
}

现在,我想要的是将obj的所有权传递给我的数据管理员并让primaryDict保留强引用,secondaryDict保留弱引用。我就是这样用C ++做的:

map<string, unique_ptr<MyBusinessObject>> primaryDict;
map<string, MyBusinessObject*> secondaryDict;

takeObj函数会接受unique_ptr<MyBusinessObject>传递给std::move的{​​{1}}。然后,它将再次移动到primaryDict,并在secondaryDict中添加一个带有原始指针的弱引用。

我的问题是 - 告诉Objective-C ARC系统以这种方式管理我的引用的正确方法是什么?

2 个答案:

答案 0 :(得分:1)

使用NSMapTable而不是NSDictionary来保存你的弱引用。检查documentation,尤其是NSMapTableOptions上的部分。

您可以使用与NSDictionary相同的行为创建一个映射表,但通过初始化来对值进行弱引用:

[NSMapTable mapTableWithKeyOptions:NSMapTableCopyIn valueOptions:NSMapTableWeakMemory]

这是Obj-C的等价物:

std::map<std::string, std::weak_ptr<MyBusinessObject>>

不会保留这些值,并且当对象解除分配时,引用将自动设置为nil。但是,表条目不会被删除,因此您可能需要检查具有nil值的条目并不时删除它们,具体取决于您期望的密钥数量。

请注意,除非您需要循环引用或实现类似缓存的操作,否则通常没有理由这样做。强引用类似于C ++中的std::shared_ptr,而Objective-C中的约定是共享对单个对象的引用,而不是与单个所有者进行复制/移动(您将最终与语言/框架作斗争)如果你尝试不同的方式)。

答案 1 :(得分:0)

那么,-takeObj:...方法的实例在传入之后拥有obj?为什么如果它与两个强引用相对而不是一个呢?简而言之,只需使用NSMutableDictionary并让两个词典都对obj有强烈的引用。对此没有任何明显的性能损失,并且基础集合没有内置支持将弱引用归零,所以如果这就是你所说的“弱”,那么无论如何你都会独立。