2012-02-08 3 views
1

У меня есть несколько проблем, связанных с NSPredicates, вот они;Написание NSPredicate

1.) Мой код выглядит следующим образом;

NSArray *arr= [self.humanArray filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"ANY name IN %@ ", nameArray]]; 

Я получил следующее исключение;

*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'The left hand side for an ALL or ANY operator must be either an NSArray or an NSSet.' 

*** Call stack at first throw: 

Когда я пишу предикат как @"name IN %@ ", nameArray. Это работает, но я думаю, что в этом может быть недостаток.

примечание: humanArray, содержит объекты HUMAN, а объект human содержит следующие атрибуты. name, age, gender, country, region.

2.) Я думаю, что я делаю здесь, это неправильно. Пользователю предоставляется возможность фильтровать self.humanArray. Пользователь может фильтровать один, более или ни один из следующих критериев;

name, age, gender, country or region. 

Мой код выглядит следующим образом;

NSArray *fRegionArray= [self.humanArray filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"regionIN %@ ", regionArray]]; 



NSArray *fCountryArray= [fRegionArray filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"country IN %@ ", countryArray]]; 



NSArray *fNameArray= [fCountryArray filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"name IN %@ ", nameArray]]; 

Этот код работает, если пользователь выбирает все атрибуты фильтра (region, country и name). Если вы посмотрите на приведенный выше код, вы заметите, что выходной массив первого предиката используется для фильтрации во втором предикате. Вот почему он ведет себя так.

Мне нужно изменить приведенный выше код, чтобы пользователь вводил любой из атрибутов для целей фильтрации. region или country или name.

ответ

1
  1. foo IN уже означает любой объект foo в указанном массиве. Вы должны использовать ANY, а затем базовое выражение (пример ANY objects.value < 13). IN является совокупным выражением.
  2. Вы можете использовать временное значение и фильтровать его только по фактически используемым атрибутам?
+0

для вопросов 1.) Так что я не могу использовать ЛЮБОЙ с IN в вышеприведенном предикате? ques 2.) Можете ли вы показать мне пример, как это сделать? – Illep

+1

для 1) просто пропустите ЛЮБОЙ, он не предназначен для использования как это 2) просто создайте изменчивый массив и добавьте объекты из результата каждого предиката, а затем удалите дубликаты –

1

Я сделал это в шахтном проекте, где мне нужно было фильтровать массив объектов на основе нескольких критериев.

NSPredicate *filterBlock = [NSPredicate predicateWithBlock: ^BOOL(id obj, NSDictionary *criteria){ 

      NSString *name = [criteria objectForKey:@"name"]; 
     NSString *gender =.................... 

     YourObject *yo = (YourObject*)obj; 
     if (yo.name isEqualToString:name && yo.gender isEqualToString:gender) { 
      // refine all your criteria 
      return YES; 
     } else { 
      return NO; 
     } 
}]; 


NSArray *result = [arrayToBeFiltered filteredArrayUsingPredicate:filterBlock]; 

Это работало, и это не так плохо в отношении скорости.

Смежные вопросы