2

controller保持する配列を持つ がありactorsます。アクターは、 によって呼び出されるオブジェクトcontrollerです。

問題:は配列をcontroller繰り返し処理し、各アクターに. アクターは、別のアクターを作成して に登録したり、コントローラーのアクター配列からアクターまたはそれ自体を削除したりできます。次の 2 つの方法でルーティングされます。actors-actionMessagecontroller

-registerActor:(Actor*)actor;
-unregisterActor:(Actor*)actor;

そのため、コントローラーがアクター配列を反復処理している間に、アクターのリストが変更される可能性があります。編集: また、新しく追加されたアクターもループを通過する必要があります。

この問題に対処するためのベストプラクティスは何ですか? 反復する前に、アクター配列のコピーを作成する必要がありますか?

4

6 に答える 6

6

可変配列のコピーを作成し、それを反復処理します。

NSArray *loopArray = [NSArray arrayWithArray: yourActorArray];

または

NSArray *loopArray = [yourActorArray copy];
//in this case remember to release in nonARC environment
于 2012-09-01T19:40:38.890 に答える
2

これは、私が通常行うことです...

NSMutableArray *discardedItems = [NSMutableArray array];
SomeObjectClass *item;

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

[originalArrayOfItems removeObjectsInArray:discardedItems];

これが役立つことを願っています。

于 2012-09-01T19:47:21.883 に答える
2

ステップごとに変更する必要がある可変配列を列挙する標準的な手順は、コピーを作成してそれを反復処理し、元の配列を変更することです。アクターの NSMutableArray はコントローラーに属するプロパティであり、 registerActor: と unregisterActor: の両方がこの配列を変更していると思います。コピーをステップ実行すると、コピーを変更せずに、メソッドを介して元のプロパティからアクターを削除できます。

NSMutableArray *actorArrayCopy = [self.actorArray copy];
for (id object in actorArrayCopy){
    //do stuff
}        

場合によっては、高速な列挙を破棄して標準の for ループを使用できますが、ここでは危険です。オブジェクトが配列に挿入または配列から削除されると、インデックスがシフトします(AFAIK)。つまり、要素をスキップしたり、要素を複数回行ったりする可能性があります。

一部の人々は、高速列挙内の別の配列に変更 (削除など) する要素を格納し、列挙が完了すると一度にすべての変更を実行しますが、要素の追加と削除には別の方法を使用しています。要素自体が何が起こるかを決定し、通知します。これは物事をより複雑にするので、おそらくコピーが最もうまくいくでしょう。

于 2012-09-01T19:51:15.657 に答える
1

これを行うことで、配列のコピーを作成することを避けることができます:

for(int i=0; i<[array count]; i++)
{
    if(condition)
    {
        [array removeObjectAtIndex:i];

        i --;
        continue;
    }
}
于 2012-09-01T19:57:35.480 に答える
1

配列の代わりにセットを使用する必要があります。次に、セットをコピーできます。操作が完了したら、差分を取得して変更内容を確認します。

于 2012-09-01T20:03:06.403 に答える