Не удается отладить ошибку iPhone Core Data - PullRequest
0 голосов
/ 21 февраля 2010

Я надеюсь, что кто-то может помочь мне отладить невероятно разочаровывающий сбой Core Data. Сначала я загружаю данные в две сущности (представляющие «выступающие» и «заголовки»), затем загружаю третью сущность для «сеансов» и пытаюсь установить отношения с «выступающими» и «заголовками». (от сеанса к докладчику и заголовок один к одному. от докладчика / заголовок к сеансу - один ко многим). Я использую целочисленный ключ для настройки каждого отношения.

Поскольку данный динамик и заголовок могут указывать на несколько сеансов, я написал функцию, которая ищет соответствующий управляемый объект и возвращает объект. Я тогда установил это для отношений.

Это прекрасно работает для взаимоотношений с докладчиком, но постоянно и ужасно падает для ВТОРОГО названия. Я несколько раз переписывал код по-разному и всегда сталкивался с одной и той же проблемой. И проблема существует независимо от того, какой заголовок идет вторым. Так что я должен сделать что-то просто в корне неправильно, но, следуя главам Core Data в More iPhone 3 Development, мне ничего не бросается в глаза. Я надеюсь, что кто-то может увидеть, что я скучаю (и был в течение нескольких дней). (Последнее замечание: сбой происходит независимо от того, сохраняю ли я файл managedObjectContext в цикле for или вне его. Всегда во втором сеансе). Моя бесконечная благодарность и первенец всем, кто может мне помочь с этим.

Вот соответствующий код, который сохраняет сущность сеанса:

    for (NSDictionary *session in self.sessions){
        NSManagedObject *newSession = [NSEntityDescription insertNewObjectForEntityForName:[sessionEntity name] inManagedObjectContext:self.managedObjectContext];
        [newSession setValue:[session valueForKey:@"ID"] forKey:@"id"];
        [newSession setValue:[session valueForKey:@"notes"] forKey:@"notes"];
        [newSession setValue:[session valueForKey:@"length"] forKey:@"length"];

        //get the speaker value;
        [newSession setValue:[self setupSpeaker:[session valueForKey:@"speaker"]] forKey:@"speaker"];
        NSLog(@"now doing title");
        //now get the title value;
        [newSession setValue:[self setupTitle:[session valueForKey:@"title"]] forKey:@"title"];
        NSLog(@"I got back this title:%@", [newSession valueForKey:@"title"]);

        }   

        if (![self.managedObjectContext save:&error]) {
            NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
            abort();

}

Вот код, который находит подходящего спикера и заглавную сущность для отношений (я понимаю, что это довольно избыточно)

-(NSManagedObject *) setupSpeaker:(NSNumber *)id {
    NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"Speaker" inManagedObjectContext:self.managedObjectContext];
    [fetchRequest setEntity:entity];

    NSPredicate *predicate = [NSPredicate predicateWithFormat:@"id==%@",id];
    [fetchRequest setPredicate:predicate];

    NSError *error;
    NSArray *items=[self.managedObjectContext executeFetchRequest:fetchRequest error:&error];
    [fetchRequest release];

    if ([items count]>=1){
        return [items objectAtIndex:0];
    }else{
        return 0;
    }
}
-(NSManagedObject *) setupTitle:(NSNumber *)id {
    NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"Title" inManagedObjectContext:self.managedObjectContext];
    [fetchRequest setEntity:entity];
    NSLog(@"now looking for: %@", id);
    NSPredicate *predicate = [NSPredicate predicateWithFormat:@"id==%@",id];
    [fetchRequest setPredicate:predicate];

    NSError *error;
    NSArray *items=[self.managedObjectContext executeFetchRequest:fetchRequest error:&error];
    [fetchRequest release];

    if ([items count]>=1){
        NSLog(@"found %@", id);
        return [items objectAtIndex:0];
    }else{
        return 0;
    }
}

И, наконец, вот что в журналах говорится о сбое:

2010-02-20 16:48:17.134 iconf[1438:207] now looking for: 1
    2010-02-20 16:48:17.136 iconf[1438:207] found 1
    2010-02-20 16:48:17.156 iconf[1438:207] I got back this title:<NSManagedObject: 0x3b11a10> (entity: Title; id: 0x3d4a3c0 <x-coredata://B76F62BD-AC82-4335-9013-7529C2471F9C/Title/p6> ; data: {
        id = 1;
        session =     (
            0x3d51640 <x-coredata:///Session/t2765697F-14C9-4282-A067-10A2413732B834>
        );
        title = "Bill Gates Speaks";
    })
    2010-02-20 16:48:17.158 iconf[1438:207] now doing title
    2010-02-20 16:48:17.158 iconf[1438:207] now looking for: 2
    2010-02-20 16:48:17.159 iconf[1438:207] found 2
    2010-02-20 16:48:17.161 iconf[1438:207] I got back this title:<NSManagedObject: 0x3b16fd0> (entity: Title; id: 0x3d4d7a0 <x-coredata://B76F62BD-AC82-4335-9013-7529C2471F9C/Title/p12> ; data: {
        id = 2;
        session =     (
            0x3b1b320 <x-coredata:///Session/t2765697F-14C9-4282-A067-10A2413732B835>
        );
        title = "Lecture on Frogs";
    })
    2010-02-20 16:48:17.161 iconf[1438:207] *** -[NSManagedObject compare:]: unrecognized selector sent to instance 0x3b11a10
    2010-02-20 16:48:17.162 iconf[1438:207] Serious application error.  Exception was caught during Core Data change processing: *** -[NSManagedObject compare:]: unrecognized selector sent to instance 0x3b11a10 with userInfo (null)
    2010-02-20 16:48:17.163 iconf[1438:207] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '*** -[NSManagedObject compare:]: unrecognized selector sent to instance 0x3b11a10'
    2010-02-20 16:48:17.163 iconf[1438:207] Stack: (

Ответы [ 2 ]

1 голос
/ 21 февраля 2010

Похоже, ваша модель данных (должна) выглядеть следующим образом:

Динамик <- >> Сессия
Заголовок <- >> Сессия

Где у каждого докладчика и заголовка есть отношение ко-многим к сеансу.

На основании этого:

Я использую целочисленную клавишу для настройки каждого отношения.

и ваш код, похоже, вы управляете отношениями вручную. Почему вы это делаете?! Это сложно и ненужно. Установите и используйте реальные отношения в вашей модели данных Core Data.

Кроме того, не используйте «id» для имени атрибута, так как это ключевое слово в target-C.

0 голосов
/ 22 февраля 2010

Спасибо, ниже приведена копия модели данных. Вы правы насчет базового макета.

http://www.freeimagehosting.net/image.php?debf5866c1.jpg

Причина, по которой я устанавливаю отношения вручную, заключается в том, что это первый раз в программе, поэтому я делаю первоначальную загрузку данных из трех отдельных списков (один для докладчика, один для заголовка, один для сеанса). Есть лучший способ сделать это? Я мог бы принципиально не понимать основные данные, но кажется, что если бы я просто создавал новый объект заголовка каждый раз, когда создавал объект сеанса, у меня было бы отношение один к одному от заголовка к сеансу, а не один к одному много отношений, которые я хочу. Таким образом, я вставил переменные id (которые я теперь переименовал без изменения ошибки), чтобы они служили ключом для первой загрузки в основные данные. После этого я, конечно, буду использовать основные данные для управления всем этим. Есть ли лучший способ сделать это?

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