2013-05-24 4 views
0

Я следующий CoreData объектов МодельCoreData NSPredicate с отношением

enter image description here

Теперь я имею вопрос в создании предиката со следующими условиями.

Fetch все те DBOpportunity ГДЕ

DBOpportunity.stateCode == 1

И

DBOpportunity.invoiceDate> = GIVEN_DATE

И

DBOpportunityLines.crmAccept == 1 ИЛИ DBOpportunityLines.crmAccept == 3

Я пробовал множество примеров и руководство по программированию от apple, но не могу этого добиться.

ответ

3

opportunitylines является отношением к-многим, поэтому существует несколько объектов DBOpportunityLines для одного объекта DBOpportunity. Если предположить, что последнее условие

DBOpportunityLines.crmAccept == 1 OR DBOpportunityLines.crmAccept == 3

следует проводить для любой из связанных объектов, вам необходимо подзапрос:

NSDate *givenDate = ...; 
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"stateCode == 1 AND invoiceDate >= %@ " 
    "AND SUBQUERY(opportunitylines, $x, $x.crmAccept == 1 OR $x.crmAccept == 3)[email protected] > 0", 
    givenDate]; 

Примечание: К сожалению, использование SUBQUERY в предикатах плохо документировано. В ссылке класса NSExpression имеется one example. См. Также Quick Explanation of SUBQUERY in NSPredicate Expression.

+0

@Marting thanx alot, это было отличное решение. Можете ли вы навестить меня в незначительной модификации вышеприведенного запроса.Я просто хочу сохранить все условия как таковые с одним дополнительным условием. В настоящее время possiblines.crmAccept должно быть 1 или 3, я хочу также включить, если нет линий возможностей с возможностью объекта. –

+1

@IrfanDANISH: Возможно, что-то вроде '' stateCode == 1 AND invoiceDate> =% @ AND (SUBQUERY (возможности, $ x, $ x.crmAccept == 1 ИЛИ $ x.crmAccept == 3). @ Count> 0 ИЛИ linelines. @ count == 0) ". –

+1

Thanx во время хита и испытания я сделал это :) –

2

Структура вашего предиката A && B && (C || D)

Настройка ваших предикаты

NSPredicate *aPredicate = [NSPredicate predicateWithFormat:@"stateCode == %d", value]; 
NSPredicate *bPredicate = [NSPredicate predicateWithFormat:@"invoiceDate >= %@", givenDate]; 

Похожие делать в cPredicate и dPredicate. Тогда первый объединить с и д с ИЛИ

NSArray *cdPredicateArray = @[cPredicate, dPredicate]; 
NSPredicate *cdPredicate = [NSCompoundPredicate orPredicateWithSubpredicates:cdPredicateArray]; 

, а затем все они с И

NSArray *allPredicateArray = @[aPredicate, bPredicate, cdPredicate]; 
NSPredicate *allPredicate = [NSCompoundPredicate andPredicateWithSubpredicates:allPredicateArray]; 

Если я неправильно понял ваш вопрос и ваша структура A && B && C || D Тогда вы должны объединить A, B и C первой (с AND), а затем объединить этот результат с D (с OR).

+1

Обратите внимание, что название организации не является частью сказуемого, так что первый из них будет просто '...«stateCode ==% d ", value]'. –

1

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

NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init]; 
NSEntityDescription *entity = [NSEntityDescription entityForName:@"opportunityLines" inManagedObjectContext:context]; 
[fetchRequest setEntity:entity]; 

NSDate *yourDate = [NSDate date]; 
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"(crmAccept==1 OR crmaccept==3) AND opportunity.stateCode==1 AND opportunity.invoiceDate>=%@", yourDate]; 
[fetchRequest setPredicate:predicate]; 

NSError *error; 

//So here you have your array of opportunitylines 
NSArray *opportunityLines = [context executeFetchRequest:fetchRequest error:&error]; 

//And this is how you get your opportunity objects 
NSArray *opportunities = [opportunityLines valueForKeyPath:@"@distinctUnionOfObjects.opportunity"]; 
Смежные вопросы