Странная ошибка в основных данных - PullRequest
1 голос
/ 12 декабря 2010

В приложении «Мой iPhone» (4.1.2) есть меню, каждая запись которого ведет к другому табличному представлению, заполненному подклассами NSManagedObject. Я использую один и тот же контроллер представления для каждого, но отличается предикат запроса на выборку, поэтому отображаются разные данные в зависимости от того, какой пункт меню выбрал пользователь. Достаточно просто.

Все отлично работает, прежде чем я на самом деле сохраняю контекст управляемого объекта. Однако после того, как приложение переходит в фоновый режим и возвращается на передний план, дела идут странно, потому что я использую это:

- (void)applicationDidEnterBackground:(UIApplication*)application {
    NSError *error = nil;
    if(managedObjectContext != nil)
        if([managedObjectContext hasChanges] && ![managedObjectContext save:&error]) {
            NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
            abort();
        }
}

Я подумал, что сейчас подходящее время для сохранения моих данных. Но после того, как это произошло, после того, как я вызвал performFetch: на моем контроллере полученных результатов, его fetchedObjects являются выбранными объектами из ПРЕДЫДУЩЕГО запроса на выборку, а не новым. То есть, если я сделаю:

// Choose menu item 1

[self.fetchedResultsController performFetch:nil]; // With fetch request 1
NSLog(@"%i objects were fetched", [[self.fetchedResultsController fetchedObjects] count]); // Items for fetch request 1

// Go back to menu, choose menu item 2 for new fetch request

[self.fetchedResultsController performFetch:nil]; // Fetch request 2
NSLog(@"%i objects were fetched", [[self.fetchedResultsController fetchedObjects] count]); // Items for Fetch request 2

// Hit home button, applicationDidEnterBackground: is called
// Relaunch
// Choose menu item 1

[self.fetchedResultsController performFetch:nil]; // With fetch request 1
NSLog(@"%i objects were fetched", [[self.fetchedResultsController fetchedObjects] count]); // Items for fetch request 2 - HUH?

Таким образом, проблема заключается в вызове save: в контексте моего управляемого объекта. Если я никогда не сохраняю данные, запросы на выборку никогда не смешиваются, как это, но когда я это делаю, это похоже на сохранение старых запросов на выборку, даже если сам fetchedResultsController создается только методом viewDidLoad моего контроллера представления. 1015 *

Кто-нибудь знает, что происходит?

ОБНОВЛЕНИЕ: больше кода.

- (void)viewDidLoad {
    delegate = (MAAppDelegate *)[[UIApplication sharedApplication] delegate];
    managedObjectContext = delegate.managedObjectContext;

    [self.fetchedResultsController performFetch:nil];
    NSUInteger count = [[self.fetchedResultsController fetchedObjects] count]; // Bug is detected here

    // ...
}

- (NSFetchedResultsController *)fetchedResultsController {
    if(_fetchedResultsController)
        return _fetchedResultsController;

    NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"Tweet" inManagedObjectContext:managedObjectContext];
    NSPredicate *predicate = nil;
    if([self.navigationItem.title isEqualToString:@"Personal"]) 
        predicate = [NSPredicate predicateWithFormat:@"account.username = %@ AND user.username = %@", delegate.currentAccount.username, delegate.currentAccount.username];
    else if([self.navigationItem.title isEqualToString:@"Favorites"])
        predicate = [NSPredicate predicateWithFormat:@"account.username = %@ AND favorited = YES", delegate.currentAccount.username];
    else
        predicate = [NSPredicate predicateWithFormat:@"account.username = %@", delegate.currentAccount.username];
    [fetchRequest setEntity:entity];
    [fetchRequest setFetchBatchSize:20];
    [fetchRequest setPredicate:predicate];

    NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"tweetID" ascending:NO];
    NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];

    [fetchRequest setSortDescriptors:sortDescriptors];
    NSFetchedResultsController *aFetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest
                                                                                                managedObjectContext:managedObjectContext
                                                                                                  sectionNameKeyPath:@"retrieved"
                                                                                                           cacheName:@"Root"];
    aFetchedResultsController.delegate = self;
    self.fetchedResultsController = aFetchedResultsController;

    [aFetchedResultsController release];
    [fetchRequest release];
    [sortDescriptor release];
    [sortDescriptors release];

    return _fetchedResultsController;
}

Ответы [ 2 ]

1 голос
/ 13 декабря 2010

Трудно сказать, не видя дополнительного кода, но проблема, с которой вы сталкиваетесь, вероятно, связана с начальными строками в вашем fetchedResultsController методе:

if(_fetchedResultsController)
        return _fetchedResultsController;

Что происходит, так это - просто предположение- вы повторно используете предыдущий _fetchedResultsController, который был настроен с использованием предиката для запроса на выборку 2. То есть в вашем viewDidLoad методе строка

[self.fetchedResultsController performFetch:nil];

не создает новый NSFetchedResultsController каквы думаете: предыдущий возвращается сразу при вызове fetchedResultsController, из-за начальных двух строк.

1 голос
/ 12 декабря 2010

Кешируете ли вы в каждом подпредставлении и, если да, используете ли вы разные имена для каждого кеша?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...