NSPredicate - не работает должным образом

У меня есть следующий код:

    NSString *mapIDx = @"98";
    NSLog(@"map id: %@", mapIDx);

    NSFetchRequest *request = [[NSFetchRequest alloc] init];

    NSEntityDescription *entity = [NSEntityDescription entityForName:@"WayPoint" inManagedObjectContext:managedObjectContext];
    [request setEntity:entity];

    //NSPredicate *predicate = [NSPredicate predicateWithFormat:@"waypoint_map_id=%@", mapIDx];
    NSPredicate *predicate = [NSPredicate predicateWithFormat:@"waypoint_map_id==%@", mapIDx];
    [request setPredicate:predicate];

    NSError *error;
    listArray = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    [request release];


    int arrayItemQuantity = [listArray count];
    NSLog(@"Array Quantity: %d", arrayItemQuantity);

    // Loop through the array and display the contents.
    int i;
    for (i = 0; i < arrayItemQuantity; i++)
    {
        NSLog (@"Element %i = %@", i, [listArray objectAtIndex: i]);
    }

    /*
    NSInteger *xCoordinate = listArray[1];
    NSInteger *yCoordinate = listArray[3];
    NSLog(@"xCoordinate: %@", xCoordinate);
    NSLog(@"yCoordinate: %@", yCoordinate);

    CLLocationCoordinate2D coordinate = {xCoordinate, yCoordinate};
    MapPin *pin = [[MapPin alloc]initwithCoordinates:coordinate];
    [self.mapView addAnnotation:pin];
    [pin release];
    */

    [listArray release];

Как видите, я пытаюсь выбрать определенные объекты из своей базы данных, все, что имеет значение waypoint_map_id, равное 98, но NSPredicate работает не так, как я ожидал. Выбираются нулевые объекты.

Есть у кого какие мысли?


person Stephen    schedule 22.07.2010    source источник


Ответы (3)


Предикат с форматом не преобразует строку "98" в число. Вместо этого он делает

waypoint_map_id == "98"

... который ищет строковый атрибут. Измените предикат на:

NSInteger mapIdx=98;
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"waypoint_map_id==%d", mapIDx];

... который возвращает предикат:

waypoint_map_id == 98
person TechZen    schedule 22.07.2010
comment
О, тогда вы уверены, что у вас есть объект WayPoint с атрибутом waypoint_map_id, равным 98? Вы можете попробовать закомментировать предикат и выгрузить все объекты WapPoint для проверки. - person TechZen; 22.07.2010
comment
Кроме того, закомментированный код выглядит странно. Первый и третий элементы в возвращаемом массиве будут WayPoint NSManagedObjects (или подклассом). Поскольку у вас нет дескриптора сортировки, назначенного выборке, они будут в случайном порядке. Затем вы назначаете их адреса как указатели на целые числа, а затем пытаетесь использовать эти адреса как двойники в определении координат. Это не сработает. Я думаю, что вы можете что-то спутать с вашими объектами. - person TechZen; 22.07.2010

Предполагая, что у вас определенно есть этот объект в вашей базе данных, попробуйте добавить кавычки вокруг значения?

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"waypoint_map_id==\"%@\"", mapIDx];

(хватаясь за соломинку!)

Ваш предикат выглядит нормально, поэтому я сразу же начал бы подозревать, что ошибка где-то еще:

  • Есть ли определенно путевая точка с таким идентификатором?
  • Является ли listArray nil, т.е. что-то еще пошло не так с запросом?

Вы не проверяете, в чем ошибка — возможно, это даст вам больше информации?

NSError *error = nil;
NSArray *results = [managedObjectContext executeFetchRequest:request error:&error];
[request release];

if (nil == results || nil != error)
  NSLog(@"Error getting results : %@", error);

listArray = [results mutableCopy];

Надеюсь, это вообще полезно!

person deanWombourne    schedule 22.07.2010
comment
спасибо, я вставил код проверки ошибок и перепроверил, ошибок не было. Определенно есть путевые точки с этим идентификатором, когда я запускаю без предиката, я вижу вывод в консоли. - person Stephen; 22.07.2010
comment
Что вы получите, если запустите его без предиката и выведете NSLog(@%@, item.waypoint_map_id); для каждого элемента в listArray? - person deanWombourne; 22.07.2010
comment
следующую строку: NSLog (@Element %i = %@, i, [[listArray objectAtIndex: i] valueForKey:@waypoint_map_id]); выводит «Элемент 1813 = 98» на консоль. - person Stephen; 22.07.2010

Проблема решена:

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"waypoint_map_id contains[cd] %@", mapIDx];
    [request setPredicate:predicate];
person Stephen    schedule 23.07.2010