2010-05-03 24 views
15

me encontré con el siguiente acceso directo en la creación de un bucle (acceso directo en comparación con los ejemplos de libros de texto he estado utilizando):Extracción de objeto desde NSMutableArray

for (Item *i in items){ ... } 

en contraposición al formato más largo:

for (NSInteger i = 0; i < [items count]; i++){ ... } //think that's right 

Si uso la versión más corta, ¿hay alguna manera de eliminar el elemento que se está iterando actualmente (es decir, 'i')? ¿O necesito usar el formato más largo?

+0

El primer bucle se conoce como el ciclo mejorado, y el segundo uno es el viejo estándar FOR loop. Aprendo esto cuando hago mi certificación Java. – Popeye

+0

Si realmente necesita eliminar elementos de la matriz mientras la itera y no puede eliminarlos luego usando 'removeObjectsInArray:' o 'removeObjectsAtIndexes:' como sugirió @Vladimir, siempre puede iterar sobre una copia de la matriz original. – Tiago

Respuesta

31

No se puede quitar objetos de la matriz, mientras que fast-enumerating que:

numeración es “seguro”, el empadronador tiene un guardia de la mutación de manera que si intento de modificar la colección durante la enumeración, una excepción es planteado.

De todos modos, ¿por qué necesita cambiar su contenedor mientras lo enumera? Considere almacenar elementos que deben eliminarse y eliminarlos de su contenedor utilizando el método removeObjectsInArray: o removeObjectsAtIndexes:.

+0

Gracias. Lo estoy cambiando al enumerarlo porque es una cola temporal. Moveré todos los elementos a otra matriz. –

+1

Si mueve * todos * los objetos a otra matriz, intente lo siguiente: '[destinationArray addObjectsFromArray: sourceArray]; [sourceArray removeAllObjects]; ' – JeremyP

+0

Sí, lo encontré, gracias. –

1

El primero es un bucle "for-each" bucle en Objective C.

* i es un puntero al elemento directa en el artículo en-Array (la mayoría de las veces esto habrá NSMutableArray).

esta manera se puede operar directamente sobre el tema:

[items removeObject: i]; 

Este (debería) de trabajo - que actualmente no estoy trabajando en mi Mac y no puedo comprobarlo. Sin embargo, podría ser que Objective-C impida la eliminación de objetos al iterar sobre la colección (eso es bastante común en la mayoría de los lenguajes).

+0

De hecho, no se puede eliminar (o modificar) un 'NSMutableArray' mientras se enumera sobre él, por lo que la llamada' removeObject: 'generará una excepción. (como explica Vladimir en su respuesta) –

9

Sólo añadir palabras clave break; después de retirar el material ...

for(id item in items) { 
    if([item isEqual:itemToDelete]) { 
     [items removeObject:item]; 
     break; 
    } 
} 
+4

@ Abdullah71 con id que nunca usas *. – rptwsthi

+0

Esto eliminará un objeto y dejará de iterar, por lo que perderá otros posibles objetos que deberían eliminarse. Así que solo use esto si necesita eliminar cero a un objeto por iteración. – marsbear

3

Una colección de Objective-C no debe ser modificado durante la enumeración.

Es posible utilizar esta variante para eliminar objetos de la colección:

for (NSInteger i = items.count - 1; i >= 0 ; i--) { 
    [items removeObjectAtIndex:i]; 
} 
+0

Imho es la forma más rápida de hacerlo correctamente, dado que está bien con su lógica de negocios atravesar la matriz de atrás hacia adelante. – marsbear

0

Puedo usar este código para esto:

for (NSUInteger i = [items count] - 1; ; i--) { 
    [items removeObjectAtIndex:i]; 
} 
+0

Bucle infinito ?! – Pang

+0

Solo hasta que obtenga -1 ... entonces falla :) – marsbear

Cuestiones relacionadas