2013-06-14 5 views
4

J'ai une grande base de données avec plus de 8000 entrées. Je veux charger et énumérer dans tableview. J'ai utilisé NSFetchedResultsController. Cela fonctionne bien sauf la mauvaise performance. J'ai trouvé le tutoriel hereNSFetchedResultsController charge les données entières et les mauvaises performances

Et ajouté ma méthode performFetch: dans la méthode viewDidLoad:. Mais cela prend 2 à 3 secondes pour charger la vue.

Ici c'est mon code.

- (void)loadFetchResultsController { 
    NSError *error; 
    if (![[self fetchedResultsController] performFetch:&error]) { 
     // Update to handle the error appropriately. 
     NSLog(@"Error occurs while fetching the foods with fetch results controller %@, %@", error, [error userInfo]); 
     exit(-1); 
    } 
} 

- (NSFetchedResultsController *)fetchedResultsController 
{ 
    if (isSearching) 
    { 
     [NSFetchedResultsController deleteCacheWithName:@"SearchResults"]; 
    } 
    NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init]; 
    NSEntityDescription *entity = [NSEntityDescription 
            entityForName:@"Food" inManagedObjectContext:_managedObjectContext]; 
    NSPredicate *hiddenPredicate = [NSPredicate predicateWithFormat:@"hidden == %@",[NSNumber numberWithBool:NO]]; 
    if (isSearching) 
    { 
     hiddenPredicate = [NSPredicate predicateWithFormat:@"(hidden == %@) AND (name contains[cd] %@ OR foodDescription contains[cd] %@)",[NSNumber numberWithBool:NO], searchTerm,searchTerm]; 
    } 
    [fetchRequest setEntity:entity]; 
    [fetchRequest setPredicate:hiddenPredicate]; 

    NSSortDescriptor *sort = [[NSSortDescriptor alloc] 
           initWithKey:@"name" ascending:YES]; 
    [fetchRequest setSortDescriptors:[NSArray arrayWithObject:sort]]; 

    [fetchRequest setFetchBatchSize:20]; 

    NSFetchedResultsController *theFetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest managedObjectContext:_managedObjectContext sectionNameKeyPath:@"name.stringGroupByFirstInitial" cacheName:(isSearching) ? @"SearchResults" : @"Root"]; 
    _fetchedResultsController = theFetchedResultsController; 
    _fetchedResultsController.delegate = self; 

    return _fetchedResultsController; 
} 

J'ai utilisé les instruments et a trouvé que l'appel performFetch: méthode charge l'ensemble des données pour la première fois lorsque viewDidLoad: appels.

enter image description here

Mon modèle de données food est comme ceci:

enter image description here

Toute idée d'améliorer les performances et se débarrasser de retard .. Toute aide serait appréciée.

+0

Le problème se produit-il uniquement avec un prédicat de recherche ou généralement? –

+0

Il se produit généralement .. Ce prédicat de recherche ne fonctionne que lorsque la recherche de la barre de recherche se produit. –

+0

@MartinR Une idée de pourquoi ça se passe ?? Est-ce que je fais quelque chose de mal? –

Répondre

0

Je crois que vous devez définir la limite d'extraction sur votre demande d'extraction, pas seulement la taille du lot. Essayez d'appeler [fetchRequest setFetchLimit: 20]; et voir si ça aide. Cela devrait amener les 20 premiers enregistrements à être récupérés. Ensuite, lorsque l'utilisateur fait défiler vos données, effectuez des requêtes d'extraction supplémentaires pour obtenir plus de données.

+1

La limite d'extraction est une limite pour une requête d'extraction complète. Cela n'agira pas comme une taille de lot. Si je définis une limite comme vous l'avez dit, je ne recevrai que 20 éléments et je n'obtiendrai rien lorsque l'utilisateur défilera. Je l'ai déjà essayé aussi. –

Questions connexes