В модели у меня есть две сущности: запись и категория.Категория один-ко-многим с записью через обратную связь.Постоянное хранилище имеет тип SQLITE, а база данных не так уж мала, около 23 МБ (17k записей).
Я использую детальный дизайн списка, чтобы показать таблицу записей и детальный просмотр записей. Представление listController используетNSFetchedResultsController.
Сборка на устройстве, если я не использую setFetchBatchSize:
CoreData: annotation: sql время выборки соединения: 15,8800s CoreData: annotation: общее время выполнения выборки:16,9198 для 17028 строк.
OMG!
Если я использую setFetchBatchSize: 25, все снова отлично работает:
CoreData: annotation: sql connectionвремя выборки: 1,1736 с CoreData: аннотация: общее время выполнения выборки: 1,1900 с для 17028 строк.
Да, это было бы здорово!Но это не так!В списке viewController, когда пользователь нажимает на запись, я выделяю подробный viewController и передаю запись в indexPath в fetchedResultsController:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
Record *record = (Record *)[fetchedResultsController objectAtIndexPath:indexPath];
RecordViewController *recordViewController= [[RecordViewController alloc] init];
recordViewController.record = record;
[self.navigationController pushViewController:recordViewController animated:YES];
[recordViewController release];
}
СЕЙЧАС, в подробном viewController у меня есть кнопка для установкизапись как любимая или нет:
- (IBAction) setFavorite {
if (![record.ISFAV intValue])
[record setValue:[NSNumber numberWithInt:1] forKey:@"ISFAV"];
else
[record setValue:[NSNumber numberWithInt:0] forKey:@"ISFAV"];
###SAVE ON THE CONTEXT HERE###
}
ОК, вы готовы?Если я нажимаю на первую запись в списке, то добавляю или удаляю ее из избранного, это происходит за 0,0046 секунды, мгновенно!Консоль с режимом отладки SQL показывает только оператор UPDATE:
CoreData: sql: BEGIN EXCLUSIVE CoreData: sql: UPDATE ZRECORD SET ZISFAV =?, Z_OPT =?ГДЕ Z_PK =?И Z_OPT =?CoreData: sql: COMMIT CoreData: аннотация: sql время выполнения: 0,0046 с
Если я прокручиваю большой список очень быстро (и, очевидно, нахожу пакетные запросы на консоли), когда я нажимаю на записьдостигнуто со многими пакетными запросами, и я добавляю \ удаляю его из избранного, много много много много (слишком много! чем больше я прокручиваю, тем больше они!) операторы SELECT появляются в консоли перед словом ОБНОВЛЕНИЕЭто означает, что общее время выполнения недопустимо (uibutton долго зависает на iphone).
Что происходит?Проблема явно связана с пакетными запросами на выборку.Больше запросов на выборку = больше операторов SELECT перед оператором UPDATE.Это один из них:
CoreData: sql: SELECT 0, t0.Z_PK, t0.Z_OPT, t0.ZCONTENT, t0.ZCONTENT2, t0.ZISUSER, t0.ZISFAV, t0.ZTITLE,t0.ZTITLE2, t0.ZID, t0.ZAUTHOR, t0.ZCATEGORY ОТ ZRECORD t0 ГДЕ t0.Z_PK IN (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?) ORDER BY t0.ZTITLE LIMIT 26
Если я удалю setFetchBatchSize, проблем не будет (но запуск требует 16 секунд).Кажется, что когда я обновляю свойство ISFAV, CoreData необходимо снова выполнить все fetchRequests, которые были необходимы для достижения этой записи, даже если я передаю эту запись в подробный viewController как объект.
Извините за длинный постЯ старался быть как можно более понятным.Большое спасибо, я схожу с ума ...