带有弱引用的NSMutableDictionary:使用CFRetain作为回调时的警告

时间:2011-02-01 21:16:01

标签: cocoa callback default nsmutabledictionary weak-references

我正在尝试创建一个可变字典,它对值对象具有弱引用(键表现正常)。 这就是我试图这样做的方式:

+ (id)mutableDictionaryUsingWeakReferencesWithCapacity:(NSUInteger)capacity
{
    CFDictionaryKeyCallBacks keyCallbacks = {0, CFRetain, CFRelease, CFCopyDescription, CFEqual, CFHash};
    CFDictionaryValueCallBacks valueCallbacks = {0, NULL, NULL, CFCopyDescription, CFEqual};    
    id<NSObject> obj = (id)(CFDictionaryCreateMutable(NULL, capacity, &keyCallbacks, &valueCallbacks));
    return [obj autorelease];
}

不幸的是,在声明keyCallbacks时,我收到了警告(从不兼容的指针类型初始化),并且我已将其跟踪到使用CFRetain和CFRelease。由于某些原因,这些回调与所需的原型不匹配(CFDictionaryRetainCallback和CFDictionaryReleaseCallback)

在文档中,它说示例CFDictionaryRetainCallback应该如下所示:

const void *MyCallBack (
   CFAllocatorRef allocator,
   const void *value
);

但现有的CFRetain被声明为

CFTypeRef CFRetain(CFTypeRef cf);

它缺少allocator参数,这就是我认为编译器发出警告的原因:它不是函数签名中的完美匹配。

有人试图做这样的事吗?

4 个答案:

答案 0 :(得分:5)

不要这样做。使用NSMapTable

答案 1 :(得分:1)

如果您只想要默认的CFRetain / CFRelease行为,这应该可行:

void MONDictionaryReleaseCallback(CFAllocatorRef allocator, const void* value) {
#pragma unused(allocator)
    assert(value);
    if (0 != value) {
        CFRelease(value);
    }
}

保留回调应该很容易从那里实现。

答案 2 :(得分:0)

我设法使用kCFTypeDictionaryKeyCallBacks常量使其工作,而不是手动声明键回调。 代码现在看起来像这样:

id<NSObject> obj = (id)(CFDictionaryCreateMutable(NULL, capacity, &kCFTypeDictionaryKeyCallBacks, &valueCallbacks));

但是,我仍然很好奇为什么我的初始代码不起作用

答案 3 :(得分:0)

如果您不介意稍微使用运行时,this是我正在为我的项目工作的东西(它适用于ATM,但它有点草率)。它动态创建您添加的任何对象的新子类,并将该对象的类设置为子类。子类保留一个对象数组,每当对象被释放时都应该通知它们。字典将自己添加到此数组中,以便在取消分配对象时可以删除该对象。