我正在解析大量数据,我最初将其插入到核心数据存储中。
稍后,我正在解析相同的XML,尽管其中一些可能已经更新。然后我做的是检查具有相同标签的现有记录,如果已存在,我用数据更新记录。
然而,虽然我的初始解析(大约11.000条记录)需要8秒左右,但更新似乎很昂贵,需要144秒(这些是模拟器运行,因此在实际设备上显着更长)。
虽然第一次很好(我正在显示进度条),但第二次是不可接受的长,我想做一些事情来提高速度(即使它发生在一个单独的线程的后台)。
不幸的是,这不是find-or-create的问题,因为XML中的数据可能已经针对单个记录进行了更改,因此每个记录都需要更新。
我对属性进行了索引,这加快了初始解析和更新,但它仍然很慢(上面的数字都带有索引)。我注意到解析/更新似乎逐渐减慢。虽然最初很快,但随着越来越多的记录被处理,它会越来越慢。
所以最后我的问题是,如果对我如何提高我更新数据集的速度有什么建议?我正在使用MagicalRecord获取记录。这是代码:
Record *record;
if (!isUpdate) {
record = [NSEntityDescription insertNewObjectForEntityForName:@"Record" inManagedObjectContext:backgroundContext];
} else {
NSPredicate *recordPredicate = [NSPredicate predicateWithFormat:@"SELF.tag == %@", [[node attributeForName:@"tag"] stringValue]];
record = [Record findFirstWithPredicate:recordPredicate];
}
答案 0 :(得分:3)
不是进行大量的提取,而是对每个实体类型执行一次查询,并按标记将它们存储在字典中,然后只检查字典是否存在具有该键的对象。您应该能够将propertiesToFetch设置为仅包含标记,并且应该减少开销。
答案 1 :(得分:1)
您可以尝试的一件事是使用模板NSPredicate,这样您就不会为每个正在执行的查找/获取重新解析格式字符串。
所以在你进入你的循环之前:
NSPredicate *template = [NSPredicate predicateWithFormat:@"SELF.tag == $RECORD_TAG"];
循环内部:
Record *record;
if (!isUpdate) {
record = [NSEntityDescription insertNewObjectForEntityForName:@"Record" inManagedObjectContext:backgroundContext];
} else {
NSPredicate *recordPredicate = [];
record = [Record findFirstWithPredicate:[template predicateWithSubstitutionVariables:[NSDictionary dictionaryWithObject:[[node attributeForName:@"tag"] stringValue] forKey:@"RECORD_TAG"]];
}
有关详细信息,请参阅Apple的Predicate Programming Guide。
答案 2 :(得分:1)
您还可以尝试将Senior的答案与属性的散列相结合。
在插入哈希属性并将该哈希存储为Record
的一种校验和属性
在更新时,您将获取的属性设置为标记和校验和,并对所有项进行一次提取。然后,当您对数据集进行迭代时,如果校验和与已获取的校验和不同,则可以获取Record
并更新它。
答案 3 :(得分:1)
所有性能问题的初始答案是运行仪器。然后,使用该数据,您可以识别问题区域。从那里开始,您可能会对提高绩效的某些方面有其他具体问题。
我们人类在识别性能瓶颈方面非常糟糕。所以,首先使用仪器。它肯定会告诉你你的时间花在哪里。