我的数据模型中有几个一对多的关系。在每种情况下,重要的是从模型中检索的数据的顺序与其插入的顺序相匹配。我在检查员中勾选了每个关系的“有序”框。我按如下方式添加数据:
NSMutableOrderedSet *set = [destinationEntity mutableOrderedSetValueForKey:relationshipKey];
[set addObject:sourceEntity];
[CoreDataFunctions saveEntity:destinationEntity];
我随后按如下方式检索该集:
NSOrderedSet *set = [sourceEntity valueForKey:relationshipKey];
在添加了数据的设备上,这可以正常工作 - 我可以添加多个实体,它们始终以正确的顺序显示。问题是在通过iCloud同步接收数据的设备上,以不同的顺序返回该集合。始终以相同的顺序提醒您,但与原始设备上输入的顺序不同。
为了解决这个问题,我添加了一个'order'属性,当将对象插入集合时,该属性由递增的整数填充。然后,我可以在从数据模型中检索该密钥后对该密钥进行排序。但是,如果NSOrderedSet没有以可预测的顺序返回,我会情不自禁地觉得有些问题。
我想知道这是否与我在设备从iCloud接收交易时在日志中看到的一些错误有关。我看了很多次,大概是每次交易一次:
***错误:此进程调用了一个NSArray-taking方法,例如initWithArray:,并传入一个NSSet对象。现在这种情况正在解决,但很快就会让你感到悲伤。
我认为这是因为数据模型中的对象是NSSet类型,而Core Data正在将它们传递给期待NSArray的东西。但是,我不知道我能做些什么,或者它是否与这个问题有关。我假设它是,因为我怀疑Core Data正在将NSOrderedSet转换为NSArray并且在此过程中丢失了排序。我不能证实这一点。
感激地收到任何建议!
答案 0 :(得分:0)
最可靠的方法是创建一个Abstract Entity
,如BaseEntity
,数据模型中的每个其他类都继承该BaseEntity
。 dateCreated
会在您awakeFromInsert
子类的NSManagedObject
中设置NSSortDescriptor
属性。
然后,当您执行获取请求时,您可以使用dateCreated
指定要排序的SQLite
,这非常快,特别是如果您使用的是ordered
。
如果您这样做,那么您可以取消选中CoreData中的Entity
按钮。
编辑:以下是托管对象子类中的排序关系的示例:
给定具有CoreData生成关系属性的实体@property (nullable, nonatomic, retain) NSSet<Entity *> *toManyRelationship;
:
@property (nullable, nonatomic, strong, readonly) NSArray<Entity *> *orderedToManyRelationship;
然后您可以创建自己的属性:
@dynamic toManyRelationship;
- (NSArray<Entity *> *)orderedToManyRelationship
{
NSSortDescriptor *dateSorter = [NSSortDescriptor sortDescriptorWithKey:@"dateCreated" ascending:YES];
return [[self.toManyRelationship allObjects] sortedArrayUsingDescriptors:@[dateSorter]];
}
这是这样实现的:
background: rgba{0,0,0,0);