7

我从通讯簿文档中的感觉和我对底层 CoreData 实现的理解表明通讯簿应该是线程安全的,并且从多个线程进行查询应该没有问题。但是我在文档中找不到任何关于线程安全的明确讨论。这提出了几个问题:

  • 在多个线程上使用 +sharedAddressBook 进行只读访问是否安全?我相信答案是肯定的。
  • 对于后台线程的写访问,您似乎应该使用 +addressBook 代替(并手动保存您的更改)。我理解正确吗?
  • 有没有人调查过在多个线程上对通讯簿进行多个同时查询对性能的影响?这应该与在多个线程上进行多个 CoreData 查询的性能非常相似。我的感觉是,通过并行查询我不会获得什么好处,因为我假设它们在遇到 SQLLite 时会序列化,但我在这里不确定。

我需要对 AddressBook 进行数十次查询(有些复杂),并且正在使用 NSOperation 在后台线程上执行此操作以避免阻塞 UI(它目前正在这样做)。我的基本问题是将最大并发操作设置为大于 1 的值是否有意义,以及如果应用程序也可能同时在另一个线程上写入 AddressBook 是否有任何危险。

4

1 回答 1

7

除非 API 说它是线程安全的,否则它不是。即使当前的实现碰巧是线程安全的,将来也可能不会。换句话说,不要在多个线程中使用 AB。

顺便说一句,它是基于 CoreData 的,你认为它是线程安全的吗?CoreData 使用线程限制模型,其中仅在单个线程上访问上下文是安全的,上下文中的所有对象都必须在同一个线程上访问。

这意味着 sharedAddressBook 如果保留一个 NSManagedObjectContext 以供使用,它将不是线程安全的。只有当 AB 每次需要做某事时都创建一个新的上下文并立即处理它,或者它为每个线程创建一个上下文并始终使用适当的上下文(可能通过在 threadDictionary 中存储对它的引用),它才是安全的. 在任何一种情况下,将任何内容存储为 NSManagedObjects 都是不安全的,因为上下文会不断被破坏,这意味着每个 ABRecord 都必须存储一个 NSManagedObjectID 以便它可以在需要时在适当的上下文中重构对象。

显然,所有这些都是可能的,可能是已经完成的,但这并不是显而易见的实现。

于 2009-07-17T09:04:05.510 回答