Ios 多条件预测

Ios 多条件预测,ios,objective-c,nspredicate,Ios,Objective C,Nspredicate,我正在尝试创建具有多个条件的NSPredicate。我已经找到了几种解决方案,但似乎没有一种适合我的方法。下面是我找到的最好看的 这是我的单谓词方法,它工作得很好: NSPredicate *predicate = [NSPredicate predicateWithFormat:@"name contains[c] %@", searchText]; filteredBusinesses = [businesses filteredArrayUsingPredicate:predicate]

我正在尝试创建具有多个条件的NSPredicate。我已经找到了几种解决方案,但似乎没有一种适合我的方法。下面是我找到的最好看的

这是我的单谓词方法,它工作得很好:

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"name contains[c] %@", 
searchText];
filteredBusinesses = [businesses filteredArrayUsingPredicate:predicate];
这是我的编辑版本,有多个条件。我不确定出了什么问题。有什么想法吗

NSPredicate *p1 = [NSPredicate predicateWithFormat:@"name contains[c] %@", searchText];
NSPredicate *p2 = [NSPredicate predicateWithFormat:@"businessArea contains[c] %@", 
searchText];

NSPredicate *predicate = [NSCompoundPredicate andPredicateWithSubpredicates:@[p1, p2]];
filteredBusinesses = [businesses filteredArrayUsingPredicate:predicate];

您发布的代码中没有任何错误,这意味着错误可能来自您通过过滤数组来计算谓词时

由于第一个谓词有效,问题在于
businessArea
关键路径

如果出现以下情况,筛选数组将引发异常:

  • 数组中有一个对象没有
    businessArea
    值(如中所示,它不是一个具有
    -businessArea
    方法的对象)
  • 该对象确实有一个
    businessArea
    值,但该值既不是
    NSString
    也不是
    nil
  • 你可以试试这个

    NSPredicate *predicate = [NSCompoundPredicate orPredicateWithSubpredicates:@[p1, p2]];
    

    除了@Nikunj的答案之外,您还可以使用NSCompoundPredicate进行和这样的操作

    Obj-C-和

    NSPredicate *predicate1 = [NSPredicate predicateWithFormat:@"X == 1"];
    NSPredicate *predicate2 = [NSPredicate predicateWithFormat:@"X == 2"];
    NSPredicate *predicate = [NSCompoundPredicate andPredicateWithSubpredicates:@[predicate1, predicate2]];
    
    let predicate1:NSPredicate = NSPredicate(format: "X == 1")
    let predicate2:NSPredicate = NSPredicate(format: "Y == 2")
    let predicate:NSPredicate  = NSCompoundPredicate(andPredicateWithSubpredicates: [predicate1,predicate2] )
    
        let predicate1 = NSPredicate(format: "X == 1")
        let predicate2 = NSPredicate(format: "Y == 2")
        let predicateCompound = NSCompoundPredicate.init(type: .and, subpredicates: [predicate1,predicate2])
    
    let predicatesAND = NSCompoundPredicate(andPredicateWithSubpredicates:[pred1,pred2])
    
    Swift-和

    NSPredicate *predicate1 = [NSPredicate predicateWithFormat:@"X == 1"];
    NSPredicate *predicate2 = [NSPredicate predicateWithFormat:@"X == 2"];
    NSPredicate *predicate = [NSCompoundPredicate andPredicateWithSubpredicates:@[predicate1, predicate2]];
    
    let predicate1:NSPredicate = NSPredicate(format: "X == 1")
    let predicate2:NSPredicate = NSPredicate(format: "Y == 2")
    let predicate:NSPredicate  = NSCompoundPredicate(andPredicateWithSubpredicates: [predicate1,predicate2] )
    
        let predicate1 = NSPredicate(format: "X == 1")
        let predicate2 = NSPredicate(format: "Y == 2")
        let predicateCompound = NSCompoundPredicate.init(type: .and, subpredicates: [predicate1,predicate2])
    
    let predicatesAND = NSCompoundPredicate(andPredicateWithSubpredicates:[pred1,pred2])
    
    Swift 3-和

    NSPredicate *predicate1 = [NSPredicate predicateWithFormat:@"X == 1"];
    NSPredicate *predicate2 = [NSPredicate predicateWithFormat:@"X == 2"];
    NSPredicate *predicate = [NSCompoundPredicate andPredicateWithSubpredicates:@[predicate1, predicate2]];
    
    let predicate1:NSPredicate = NSPredicate(format: "X == 1")
    let predicate2:NSPredicate = NSPredicate(format: "Y == 2")
    let predicate:NSPredicate  = NSCompoundPredicate(andPredicateWithSubpredicates: [predicate1,predicate2] )
    
        let predicate1 = NSPredicate(format: "X == 1")
        let predicate2 = NSPredicate(format: "Y == 2")
        let predicateCompound = NSCompoundPredicate.init(type: .and, subpredicates: [predicate1,predicate2])
    
    let predicatesAND = NSCompoundPredicate(andPredicateWithSubpredicates:[pred1,pred2])
    

    NSCompoundPredicate接受了整容。以防有人正在寻找Swift 5+版本:

    NSPredicate *predicate1 = [NSPredicate predicateWithFormat:@"X == 1"];
    NSPredicate *predicate2 = [NSPredicate predicateWithFormat:@"X == 2"];
    NSPredicate *predicate = [NSCompoundPredicate andPredicateWithSubpredicates:@[predicate1, predicate2]];
    
    let predicate1:NSPredicate = NSPredicate(format: "X == 1")
    let predicate2:NSPredicate = NSPredicate(format: "Y == 2")
    let predicate:NSPredicate  = NSCompoundPredicate(andPredicateWithSubpredicates: [predicate1,predicate2] )
    
        let predicate1 = NSPredicate(format: "X == 1")
        let predicate2 = NSPredicate(format: "Y == 2")
        let predicateCompound = NSCompoundPredicate.init(type: .and, subpredicates: [predicate1,predicate2])
    
    let predicatesAND = NSCompoundPredicate(andPredicateWithSubpredicates:[pred1,pred2])
    

    let predicatesOR = NSCompoundPredicate(orPredicateWithSubpredicates:[pred1,pred2])
    

    首先,我怀疑您的两个基本谓词可能有缺陷。从对象名称“business”判断,它是一个集合,即
    NSArray
    NSSet
    nsdictionary
    。在这种情况下,
    “name包含[c]'mmm'
    在对整个集合求值时没有意义,应该崩溃。它缺少一个集合运算符(ANY、ALL、SOME),例如
    “任何名称都包含[c]'mmm'”

    啊。。。现在我明白了。。。您正在使用谓词过滤NSArray,这意味着谓词将分别对每个项执行。所以你的谓词是正确的

    现在。。。组合谓词的最简单方法是在格式字符串级别!你怎么了

    NSPredicate *p1 = [NSPredicate predicateWithFormat:@"name contains[c] %@ AND businessArea contains[c] %@", nameToSearch, areaToSearch]; 
    
    如果您坚持以艰难的方式进行,那么构建复合NSPredicate也应该是可行的——只有您对两个条件使用了相同的搜索文本,这可能会导致谓词永远不匹配


    我给您的建议是,在评估筛选数组的行上放置一个断点,并在筛选之前停止,然后在调试器中使用调试器命令
    po p1
    打印谓词描述,您将看到谓词的最终形式,并能够确定您是否正确构建了它。

    您希望得到什么?我希望能够在我的searchbardelegage中键入多种类型的信息。相反,它会崩溃:(粘贴StackTrace)如果您所做的只是过滤数组,为什么不使用一个块谓词?@matt,我该怎么做?…一个
    谓词与
    谓词不同。OP希望这两个条件都适用于要收集的项。