在Cocoa中,如果我想在NSMutableArray中循环并删除符合特定条件的多个对象,那么在每次删除对象时不重新启动循环的最佳方法是什么?

谢谢

编辑:只是澄清一下——我在寻找最好的方法,例如,比手动更新索引更优雅的方法.例如C++中我可以做的;

iterator it = someList.begin();

while (it != someList.end())
{
    if (shouldRemove(it))   
        it = someList.erase(it);
}

推荐答案

为了清楚起见,我喜欢做一个初始循环,收集要删除的项目.然后我删除它们.下面是一个使用Objective-C2.0语法的示例:

NSMutableArray *discardedItems = [NSMutableArray array];

for (SomeObjectClass *item in originalArrayOfItems) {
    if ([item shouldBeDiscarded])
        [discardedItems addObject:item];
}

[originalArrayOfItems removeObjectsInArray:discardedItems];

那么,指数更新是否正确,或者其他一些小的簿记细节就毫无疑问了.

编辑后添加:

在其他答案中已经指出,逆公式应该更快.i、 e.如果你遍历数组,并组成一个新的数组来保存对象,而不是丢弃对象.这可能是真的(不过分配新数组和丢弃旧数组的内存和处理成本如何?)但即使速度更快,它也可能不像简单的实现那样重要,因为NSArray的行为不像"普通"数组.他们说的是实话,但他们走的是另一条路.See a good analysis here:

逆公式可能更快,但我从来不需要关心它是否更快,因为上面的公式总是足够快,可以满足我的需要.

对我来说,带回家的信息是使用任何你最清楚的公式.仅在必要时进行优化.我个人觉得上面的公式最清晰,这就是为什么我使用它.但是如果相反的公式对你来说更清楚,那就去做吧.

Objective-c相关问答推荐

NS_ASSUME_NONNULL_BEGIN 宏

iOS8:退出应用程序后不久出现蓝条“正在使用您的位置”

如何修复“UIPopoverController 已弃用”警告?

iOS9 - 这个应用程序正在从后台线程修改自动布局引擎——在哪里?

将谷歌 map 添加为子视图会使 iOS 应用程序因 exc_bad 崩溃

未调用 cellForItemAtIndexPath 但 numberOfItemsInSection 调用

Facebook 的 UIActivityViewController 不显示默认文本

iOS:警告“try 呈现其视图不在窗口层次结构中的 ViewController”

Cocoapods ld:找不到-lPods-Projectname 的库

如何在 Objective-C 中添加具有自己的 UIViewController 的子视图?

如何获得本地化的 Cancel、Done 等?

警告:格式字符串不是字符串文字(可能不安全)

升级到 Xcode 5.1 和 iOS 7.1 后,在 segue 过渡期间导航栏上出现暗影

如何在 Xcode 中将内容打印到控制台?

点击手势识别器 - 哪个对象被点击了?

带有 NSBlockOperation 和队列的 NSURLSession

字符串的静态 NSArray - 如何/在哪里初始化视图控制器

如何更改 UICollectionView 中的滚动方向?

如何将 UInt32 设置为最大值

以编程方式设置 UIView 的自动调整大小掩码?