1

我有一个装满字典的 NSArray。

我想遍历它并找到所有具有与单独数组中存在的任何字符串对象匹配的键值的字典。

然后,我想将其添加到找到的所有对象的新结果数组中。

这就是我现在的做法,但我想知道是否有更有效和更快的方法来做到这一点。

NSArray *arrayOfDictionaries, *arrayOfIDs;

NSMutableArray *results = [NSMutableArray array];

for (NSDictionary *dict in arrayOfDictionaries) {

    for (NSString *userID in arrayOfIDs) {

        if ([userID isEqualToString:dict[@"user_id"]]) {

            [results addObject:dict];

        }
    }
}

return results;
4

2 回答 2

2

NSArray containsObject:是的,通过使用以下方法,您的代码可能会更简单一些:

NSArray *arrayOfDictionaries, *arrayOfIDs;

NSMutableArray *results = [NSMutableArray array];

for (NSDictionary *dict in arrayOfDictionaries) {

    if ([arrayOfIDs containsObject:dict[@"user_id"]) {

        [results addObject:dict];

    }
}

return results;

请注意,尽管此代码更易于阅读和理解,但它仍然具有与您的原始方法相似的运行时复杂性。

这是因为尽管您发布的代码N^2在中间具有显式的运行时复杂性(嵌套的 for 循环),而我的新版本显然只有N复杂性,但containsObject:调用包含一个循环,因此仍然存在N^2复杂性。

如果您希望您的算法更有效——并且只有在这很重要的情况下,不要过早地进行优化!-- 您可以使用 anNSSet而不是 anNSArray来存储usersIDs. 这会更快,因为NSArray查找是线性时间,而NSSet使用散列进行查找并且比线性运行时查找更好。

请注意,如果要将自己的自定义对象放入 中NSSet,则应覆盖该对象上的isEquals:and hashcode。有关详细信息,请参阅覆盖 isEqual: 和哈希的最佳实践

于 2013-11-05T09:44:27.743 回答
1

您可以更进一步,过滤您的初始NSArray值并获得一组索引。

NSIndexSet *results = [NSIndexSet indexSet];    

results = [arrayOfDictionaries indexesOfObjectsPassingTest:^BOOL(NSDictionary* obj, NSUInteger idx, BOOL *stop) {
    return [arrayOfIDs containsObject:obj[@"user_id"]];
}];

请注意,containsObject如果您使用NSSetfor yourarrayOfIDs而不是NSArray.

如果您想要更多选项来过滤数组,请检查此stackoverflow 线程

于 2013-11-05T09:50:52.970 回答