核心数据:fetch是否必须访问持久存储?

说我这样做:

NSManagedObjectContext *context = #a managed object context"; NSString *entityName = #an entity name#; NSFetchRequest *requestForAll = [NSFetchRequest requestWithEntityName:entityName]; NSArray *allObj = [context executeFetchRequest:requestForAll]; for (NSString *name in allNamesArray){ NSFetchRequest *requestForOne = [NSFetchRequest requestWithEntityName:entityName]; requestForOne.predicate = [NSPredicate predicateWithFormat:@"name == %@",name]; NSArray *ObjsWithName = [context executeFetchRequest:requestForOne]; #do some work with the obj# } 

循环中的提取是否每次都会导致访问持久性存储? 或者那些提取只会在coredata的行缓存中执行?

编辑我写了一段测试代码:你需要创建一个名为“Person”的核心数据实体,它应该有一个名为“name”的属性,它的类型是string。

使用此代码填充一些数据:

 self.array = @[@"alkjsdfkllaksjdf",@"asldjflkajdklsfjlk;aj",@"aflakjsdl;kfjalksdjfklajkldhkl;aj",@"aljdfkljalksdjfl;j" ,@"flajdl;kfjaklsdjflk;j",@"akldsjfklajdslkf",@"alkdjfkljaklsdjflkaj",@"alsdjflkajsdflj",@"adlkfjlkajsdfkljkla",@"alkdjfklajslkdfj"]; NSString *firstRunKey = @"oh its first run!"; NSString *firstRun = [[NSUserDefaults standardUserDefaults] objectForKey:firstRunKey]; if (!firstRun) { for (NSString *name in self.array) { Person *p = [NSEntityDescription insertNewObjectForEntityForName:@"Person" inManagedObjectContext:self.managedObjectContext]; p.name = name; } } [self.managedObjectContext save]; [[NSUserDefaults standardUserDefaults] setObject:firstRunKey forKey:firstRunKey]; [[NSUserDefaults standardUserDefaults] synchronize]; 

分析这两种方法,你会发现使用CoreData花费的时间远远超过usingFilterArray!

 static int caseCount = 1000; -(void)usingCoreData { NSLog(@"core data"); NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"Person"]; NSArray *allPersons = [self.managedObjectContext executeFetchRequest:request error:nil]; for (int i = 0; i < caseCount; i++){ for (NSString *name in self.array) { request.predicate = [NSPredicate predicateWithFormat:@"name == %@",name]; NSArray *result = [self.managedObjectContext executeFetchRequest:request error:nil]; } } } -(void)usingFilterArray { NSLog(@"filter array"); NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"Person"]; NSArray *allPersons = [self.managedObjectContext executeFetchRequest:request error:nil]; for (int i = 0; i < caseCount; i++){ for (NSString *name in self.array) { NSArray *array = [allPersons filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"name == %@",name]]; } } } 

我猜我需要自己回答我的问题。

我对它进行了测试,发现每次执行获取时,核心数据都会将NSFetchRequest转换为SQL命令并调用数据库查询,查询结果首先是NSManagedObjectIDs,应用缓存从NSManagedObjectID获取NSManagedObject。

总之,它缓存对象,但不缓存查询结果。

这意味着您执行相同的NSFetchRequest 10次,它将查询您的持久存储10次,事件虽然您将获得相同结果的10倍。 因此在这种情况下,内存中的过滤数组将比获取更好。

获取将在可用时来自指定的缓存。

编辑:这是一个很棒的教程的链接,该教程展示了如何设置使用缓存的NSFetchedResultsController

http://www.raywenderlich.com/?p=999