我对使用NSMutableDictionary时的线程安全性有一个问题.

主线程正在从NSMutableDictionary读取数据,其中:

  • keys 是NSString
  • 值为UIImage

异步线程正在将数据写入上述字典(使用NSOperationQueue)

如何使上述词典线程安全?

我应该把NSMutableDictionary英镑换成atomic英镑吗?或者我需要做任何额外的改变吗?

@property(retain) NSMutableDictionary *dicNamesWithPhotos;

推荐答案

NSMutableDictionary不是线程安全的数据 struct ,仅仅将属性标记为atomic并不能确保底层数据操作实际上是以原子方式(以安全的方式)执行的.

为了确保以安全的方式完成每个操作,您需要用锁保护字典上的每个操作:

// in initialization
self.dictionary = [[NSMutableDictionary alloc] init];
// create a lock object for the dictionary
self.dictionary_lock = [[NSLock alloc] init];


// at every access or modification:
[object.dictionary_lock lock];
[object.dictionary setObject:image forKey:name];
[object.dictionary_lock unlock];

您应该考虑滚动自己的NSDictionary,简单地将调用委托给NSMutable字典,同时保持锁:

@interface SafeMutableDictionary : NSMutableDictionary
{
    NSLock *lock;
    NSMutableDictionary *underlyingDictionary;
}

@end

@implementation SafeMutableDictionary

- (id)init
{
    if (self = [super init]) {
        lock = [[NSLock alloc] init];
        underlyingDictionary = [[NSMutableDictionary alloc] init];
    }
    return self;
}

- (void) dealloc
{
   [lock_ release];
   [underlyingDictionary release];
   [super dealloc];
}

// forward all the calls with the lock held
- (retval_t) forward: (SEL) sel : (arglist_t) args
{
    [lock lock];
    @try {
        return [underlyingDictionary performv:sel : args];
    }
    @finally {
        [lock unlock];
    }
}

@end

请注意,因 for each 操作都需要等待锁并保持它,所以它的可扩展性不强,但在您的情况下可能已经足够好了.

如果你想使用一个合适的线程库,你可以使用TransactionKit library,因为他们有TKMutableDictionary,这是一个多线程的安全库.我个人还没有使用过它,而且它似乎是一个正在开发的库,但您可能想try 一下.

Objective-c相关问答推荐

单例实例与类方法

我在哪里可以找到 info.plist 文件?

如何更改 UIButton 的突出显示 colored颜色 ?

向 iOS 应用程序添加自定义字体以查找其真实姓名

iOS 心率检测算法

iOS - 应用程序关闭时的核心位置和地理围栏

来自 NSString 的 NSJSONSerialization

反编译 Objective-C 库

NSSet 到 NSArray 转换调用 objectAtIndex?

以流畅的动画显示/隐藏导航栏

AdMob 因 [GADObjectPrivate changeState:] 崩溃:无法识别的 Select 器

如何在 NSSet 或 NSArray 中搜索具有特定属性的特定值的对象?

在 Objective C 中,你能判断一个对象是否具有特定的属性或消息吗?

IOHIDFamily 的神秘控制台错误

AVAssetImageGenerator 提供旋转的图像

UICollectionView 仅在用户双击时调用 didSelectItemAtIndexPath,当用户单击时不会调用

-[MyClassName copyWithZone:] 无法识别的 Select 器发送到实例

Objective-C 中的 NSString indexOf

检测 UITableView 滚动

最大 CGFloat 值是否有常数?