Swift 如何为父实体满足NSPredicate的子实体创建FetchRequest谓词
我有两个核心数据实体:Swift 如何为父实体满足NSPredicate的子实体创建FetchRequest谓词,swift,core-data,nspredicate,Swift,Core Data,Nspredicate,我有两个核心数据实体:Parent和Child。 Parent具有子集合的属性children 每个子项都有一个链接到其父项的父项属性和一个年龄属性。 (我的数据比这更复杂,但这与问题无关) 我有一个NSPredicate用于选择一组父母的Parent实体,还有一个NSPredicate用于选择基于年龄的实体的Child实体 我要做的是为FetchRequest构造一个NSPredicate,它返回满足两个谓词的子实体集 我知道我可以检索满足其谓词(“父级”)的父级实体数组,然后有一个子谓词,类
Parent
和Child
。
Parent
具有子集合的属性children
每个子项
都有一个链接到其父项的父项
属性和一个年龄
属性。
(我的数据比这更复杂,但这与问题无关)
我有一个NSPredicate
用于选择一组父母的Parent
实体,还有一个NSPredicate
用于选择基于年龄的实体的Child
实体
我要做的是为FetchRequest
构造一个NSPredicate
,它返回满足两个谓词的子实体集
我知道我可以检索满足其谓词(“父级
”)的父级
实体数组,然后有一个子谓词,类似于NSPredicate(格式:“Parent IN%@”,parents)
,并将其包含在复合词中并与子谓词一起,但可能会有数百个家长遇到他们的谓词,在我看来,有两个单独的查询只是一个拼凑
FetchRequest
需要是FetchRequest
,因为它在SwiftUI视图中使用,所以我不能只构建一个结果数组
我怀疑我可以使用子查询谓词来实现这一点,但我无法确定如何将父谓词嵌入子查询。我在父实体的谓词字符串中遇到类似subpredicate TRUEPREDICATE问题的错误
希望这有意义?有什么想法或建议吗
谢谢如果从子项
到父项
的关系为一,则不需要子查询。在父谓词的格式字符串中(您可以通过谓词格式
获得),可以将字符串中的每个父属性名称替换为子属性的键路径,即
attribute
变为parent.attribute
然后,可以使用NSCompoundPredicate
的和predicatewithsubpredicates将结果谓词与子谓词组合
如果无法解析谓词格式,另一个选项是使用NSFetchRequestExpression
将一次提取的结果作为参数传递给另一次提取(它将转换为SQL子选择)。大概是这样的:
let parentFetch = Parent.fetchRequest()
parentFetch.predicate = parentPredicate // your existing predicate to fetch the parent objects
parentFetch.resultType = .managedObjectIDResultType
let ctxtExp = NSExpression(forConstantValue: managedObjectContext)
let fetchExp = NSExpression(forConstantValue: parentFetch)
let fre = NSFetchRequestExpression.expression(forFetch: fetchExp, context: ctxtExp, countOnly: false)
let childFetch = Child.fetchRequest()
let subPredicate = NSPredicate(format:"parent IN %@",fre)
let combinedPredicate = NSCompoundPredicate(andPredicateWithSubpredicates: [subPredicate, childPredicate]) // childPredicate is you existing predicate to fetch the correct Child objects
childFetch.predicate = combinedPredicate
... proceed to execute the fetch against the relevant context
父实体的谓词是什么?它是由一组用户输入条件生成的谓词,因此会发生变化。在我询问的查询中,我通过返回NSPredicate的函数访问它。每个子项只有一个父项?是的,它是一个->多个(父项->子项)但是,父谓词可能涉及多达10个属性,这些属性在运行时由应用程序用户设置不同的匹配条件,因此可靠地搜索和替换谓词字符串中的每个属性名称的公式在运行时非常重要,并且可能容易出错。如果有办法的话,我更愿意使用未更改的父谓词,因为这已经被完全测试过了Hanks,我认为这看起来很有希望,特别是如果它转换为SQL子查询的话。明天我会试一试(我在英国,所以现在很晚了!)我不确定这是否有效-子查询抛出异常,抱怨它无法生成SQL:***由于未捕获的异常“NSInvalidArgumentException”终止应用程序,原因是:'未实现谓词的SQL生成:(父项在获取中((实体:父;谓词:(startDate>=CAST(599529600.000000,“NSDate”)和(activityType==“Ride”);排序描述符:(());类型:NSManagedObjectResultType;IncludePropertyValue:NO;),NO))“
奇怪。您能显示您的实体定义和父谓词吗?我的错误:再次查看,当我复制您建议的代码时,我没有将字符串“parent IN…”更改为子实体上的实际父实体属性名称(它不是‘parent’…).刚刚修好,效果很好!谢谢你的建议,我学到了一些新东西。。。