查找NSMutableArrays的交集

我有三个NSMutableArray包含名称,根据不同的标准添加到列表中。

这里是我的数组伪代码:

NSMutableArray *array1 = [@"Jack", @"John", @"Daniel", @"Lisa"]; NSMutableArray *array2 = [@"Jack", @"Bryan", @"Barney", @"Lisa",@"Penelope",@"Angelica"]; NSMutableArray *array3 = [@"Jack", @"Jerome", @"Dan", @"Lindsay", @"Lisa"]; 

我想find第四个数组,其中包括这三个数组的交集。 在这种情况下,例如它将是:

 NSMutableArray *array4 = [@"Jack",@"Lisa"]; 

因为所有这三个数组都有jack和lisa作为元素。 有没有简单的做这个?

使用NSMutableSet

 NSMutableSet *intersection = [NSMutableSet setWithArray:array1]; [intersection intersectSet:[NSSet setWithArray:array2]]; [intersection intersectSet:[NSSet setWithArray:array3]]; NSArray *array4 = [intersection allObjects]; 

唯一的问题是,你失去了元素的sorting,但我认为(在这种情况下),这没关系。


正如已经在评论中指出的(感谢Q80 !),iOS 5和OS X 10.7添加了一个名为NSOrderedSet的新类(带有Mutable子类),允许您在保持顺序的同时执行相同的交集操作。

关于使用谓词的交叉点真的很好的教程

数组交叉和差异

看看这个post 。

简而言之:如果你可以使用NSSet而不是NSArray,那么它是微不足道的(NSMutableSet有intersectSet: :)。

否则,您可以从您的NSArray生成一个NSSet并返回到上述情况。

 NSMutableArray *first = [[NSMutableArray alloc] initWithObjects:@"Jack", @"John", @"Daniel", @"Lisa",nil]; NSMutableArray *seconds =[[NSMutableArray alloc] initWithObjects:@"Jack", @"Bryan", @"Barney", @"Lisa",@"Penelope",@"Angelica",nil]; NSMutableArray *third = [ [ NSMutableArray alloc]init]; for (id obj in first) { if ([seconds containsObject:obj] ) { [third addObject:obj]; } } NSLog(@"third is : %@ \n\n",third); 

OUTPUT:

第三个是:(

 Jack, Lisa 

这比NSSet方法更清洁,你不会失去原来的顺序。

 NSPredicate *predicate = [NSPredicate predicateWithFormat:@"self IN %@ AND self IN %@", array2, array3]; NSArray *array4 = [array1 filteredArrayUsingPredicate:predicate]; 

这是来自以上链接的工作变体

 NSPredicate *intersectPredicate = [NSPredicate predicateWithFormat:@"SELF IN %@", @[@500, @400, @600]]; NSArray *intersect = [@[@200, @300, @400] filteredArrayUsingPredicate:intersectPredicate];