iOS 15.1下使用NSPredicate进行数组过滤出现性能问题求助
问题原因
这是iOS 15.1系统底层对NSPredicate执行逻辑的优化失误导致的官方性能退化问题,大量开发者在该版本都遇到了相同的数组过滤变慢问题,该问题并未出现在官方发布说明中,后续在iOS 15.2正式版已经被官方修复。
可行的兼容解决方案
- 替换NSPredicate过滤逻辑为手动遍历匹配,是改动成本最低、兼容性最好的临时修复方案,同逻辑下在iOS 15.1上性能可恢复至iOS 15.0.2的水平,示例代码如下:
NSMutableArray *result = [NSMutableArray array]; [data enumerateObjectsUsingBlock:^(id _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { // 此处匹配逻辑和原有NSPredicate保持一致 if ([obj valueForKey:@"ID"] == value || [[obj valueForKey:@"ID"] isEqual:value]) { [result addObject:obj]; } }];
- 针对高频过滤同一份数据源的场景,可以提前将数组元素按照过滤键做字典映射,直接通过键取值,性能比遍历过滤更高:
// 数据源更新时同步更新映射字典 NSMutableDictionary *idToObjectMap = [NSMutableDictionary dictionary]; [data enumerateObjectsUsingBlock:^(id _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { id key = [obj valueForKey:@"ID"]; if (key) { idToObjectMap[key] = obj; } }]; // 过滤时直接取值 id targetObject = idToObjectMap[value];
- 若应用可提升最低支持系统版本到iOS 15.2及以上,无需修改任何原有代码,系统层面已经修复了该性能问题,原有
NSPredicate逻辑的运行速度会恢复正常。
内容的提问来源于stack exchange,提问作者Vaibhav Bansal
相关产品推荐
相关产品推荐

