如何使用 NSPredicate 通过 CoreData 中的 NSSet 属性的元素过滤对象?

Posted

技术标签:

【中文标题】如何使用 NSPredicate 通过 CoreData 中的 NSSet 属性的元素过滤对象?【英文标题】:How to use NSPredicate to filter objects by the element of their NSSet property in CoreData? 【发布时间】:2017-02-05 16:22:29 【问题描述】:

我有两个班级,一个叫Folder,另一个叫Entry

在我的数据模型中,一个文件夹会包含多个条目,一个条目可以包含在不同的文件夹中。

所以每个文件夹都有一个folderID 来标识自己,以及一个名为entries 的关系,用于包含Entry 实例。每个条目都有一个名为superFolders 的反向关系,它指向包含它的文件夹。

现在是我的问题。在这里我得到一个folderID。我想使用这个和NSFetchRequest 来获取Core Data 中这个特殊文件夹包含的所有entries。以下是主要代码:

let fetchRequest = NSFetchRequest<Entry>(entityName: "Entry")
fetchRequest.predicate = NSPredicate(format: "(ANY folder in %K).folderID = %i", #keyPath(Entry.superFolders), folerID)

上面代码中的格式字符串不正确,但它主要解释了我的意思。由于superFolders属性实际上是Core Data中的NSSet,所以我不能使用superFolders.folderID == %i作为判断条件。我真正想要的是找到其superFolder 属性包含任何元素 的所有条目,其folderID 属性与给定的folderID 匹配。

那么可以使用NSPredicate 来表达我对Core Data 的意思吗?

【问题讨论】:

【参考方案1】:

你想要:

let fetchRequest = NSFetchRequest<Entry>(entityName: "Entry")
fetchRequest.predicate = NSPredicate(format: "ANY superFolders.folderID = %@", folderID)

见NSPredicate reference

如果您在superFolders 关系上有更复杂的匹配,则需要使用SUBQUERY,但在这种情况下,一个简单的ANY 谓词可以正常工作。

【讨论】:

感谢您的回答。您提供的代码完美运行。我从官方文档中找到了一个类似的question 和一个example。这真的很简单。

以上是关于如何使用 NSPredicate 通过 CoreData 中的 NSSet 属性的元素过滤对象?的主要内容,如果未能解决你的问题,请参考以下文章

如何使用 NSPredicate 捕获子对象?

iPhone如何使用NSPredicate按父实体过滤Core Data?

我们如何使用 NSPredicate 搜索所有记录而不是设置 fetchController nil?

如何制作正确过滤本地字符的 NSPredicate?

NSPredicate 通过 NSSet 搜索

使用 NSPredicate 过滤 NSFileManger 内容以获取文件“模式”列表