-3

NSMutableArray 内の特定のインデックスの値を新しい値に置き換えると、古い値がメモリに保持されます。修正すべきハックは、すべてのループの前に新しい NSMutableArray を初期化することです。

再現する手順:

- (id) init{
    self.overlays = [[NSMutableArray alloc] initWithCapacity: [self.anotherArray count]];
}

- (void) someOtherMethod{
    for(int i = 0 ; i < self.anotherArray ; i++){
        UIView *view = [[UIView alloc] initWithFrame:CGRectMake(x, y, width, height)];
        [view setBackgroundColor:[UIColor colorWithRed:0 
                                                green:0 
                                                 blue:0 
                                                alpha:1]];
        [view setAlpha: .2];
        [self.overlays insertObject:view atIndex: i]
    }
}

- (void) main{
    for(int i = 0 ; i < 4 ; i++){
        [myObject someOtherMethod];
    }
}

insertObject:atIndex は、配列内のそのインデックスの古い値を解放しないため、効果的にメモリ リークを引き起こします。

私はバグレポートを提出し、Apple は次のように回答しました。

insertObject:atIndex: は定義どおりに動作しています。置換ではなく、挿入を行っています。置換が必要な場合は、代わりに -replaceObjectAtIndex:withObject: を使用する必要があります。

そのインデックスで古いオブジェクトへの参照を常に失うため、insertObject:atIndex: がどのように役立つでしょうか。

これは単に、古いドキュメントの定義を満たしているため、問題の修正を避けるためですか?

4

2 に答える 2

12

2 つの方法は異なることを行います。次の配列を想像してください。

NSMutableArray *anArray = [@[ @1, @2, @3 ] mutableCopy];

position に要素を挿入1すると、次のようになります。

[anArray insertObject:@4 atIndex:1];

配列は と等しくなり@[ @1, @4, @2, @3 ]ます。別の要素を削除せずに、新しい要素が挿入されます。

代わりに、次のように position の要素を置き換えると:1

[anArray replaceObjectAtIndex:1 withObject:@4];

あなたが得る@[ @1, @4, @3 ]。その場所にあった以前のオブジェクトが削除されます。

于 2012-12-18T20:52:16.140 に答える
3

insertObject:atIndexすでに指摘したように、古いアイテムは削除されません。代わりに、指定したインデックスに新しいアイテムを挿入します。このメソッドを呼び出すと、配列の要素数が 1 増加します。

replaceObjectAtIndex:withOjbectこれは、置換である とは異なります。配列の要素数は変わりません。

Insert はまさにそれを行います。5 つの要素を持つ配列を考えてみましょう。 を呼び出すと[myArray insertObject:insertedObj atIndex:1];、myArray インスタンスには 6 つの要素がありinsertedObj、最初のインデックスに挿入されます。

于 2012-12-18T20:51:40.267 に答える