2011-06-21 11 views
14

Ho una matrice mutabile vuota. È possibile inserire oggetti nell'indice 2, ad esempio, mentre non c'è nulla nell'indice 0 e 1? Intendo aumentare la capacità in modo dinamico o qualcosa di simile. .Saluti.NSMutableArray insert object all'indice

+1

Hmm Perché dovresti desiderare di farlo? :) – Mikael

+2

Ne ho bisogno per il mio mini progetto all'università.:) – GeRyCh

risposta

40

NSMutableArray non è un array sparse; non consente slot vuoti che possono essere compilati in seguito. initWithCapacity: solo suggerimenti per l'array che verrà riempito per un determinato importo; in genere non è necessario in pratica e, a meno che tu non sappia esattamente quanti oggetti stai andando a spingere nell'array, non preoccuparti di chiamarlo (usa solo init).

Un array mutabile si ingrandirà in modo efficiente in termini di dimensioni con l'aggiunta di oggetti.

Se è necessaria una struttura dati che supporti "buchi", quindi utilizzare qualcos'altro o inserire un oggetto segnaposto negli slot che si suppone siano vuoti.

I.e. se si voleva una matrice con 10 slot, si potrebbe fare:

NSMutableArray *a = [NSMutableArray array]; 
for(int i = 0; i<10; i++) [a addObject: [NSNull null]]; 

si può quindi controllare se l'oggetto recuperato isEqual: [NSNull null] per sapere se lo slot è vuoto o no. Ed è possibile utilizzare replaceObjectAtIndex:withObject: per attaccare un oggetto a un indice specifico.

Oppure è possibile utilizzare una diversa struttura dati; per esempio un dizionario con gli indici come funzionano le chiavi.

+0

È possibile aggiungere un paio di metodi di categoria per aggiungere automaticamente gli oggetti 'NSNull' secondo necessità e controllare se un elemento è l'oggetto nullo e restituire invece nil. Ecco come l'ho fatto: http://cutecoder.org/programming/behold-holy-array/ – adib

11

È possibile utilizzare uno NSPointerArray per quello.

NSPointerArray è una raccolta mutevole modellato NSArray ma può anche contenere valori NULL, che può essere inserita o estratta (e che contribuiscono al conteggio dell'oggetto). Inoltre, a differenza degli array tradizionali, è possibile impostare direttamente il conteggio dell'array .


NSPointerArray è disponibile in OS X v10.5 e versioni successive e iOS 6.0 e versioni successive. Se il target una versione inferiore del sistema operativo è possibile, ad esempio:

  • Utilizzare un NSMutableDictionary, si avvolge indici in NSNumber s e utilizzarli come chiavi.

  • Utilizzare un NSMutableArray e riempire i "buchi" con gli oggetti NSNull.

+0

Yup; Avrei dovuto accennare a questo. NSPointerArray è una classe incredibilmente utile! Tuttavia, NSPointerArray non è disponibile su iOS IIRC. – bbum

+1

Vero. Ho controllato se la domanda è stata taggata iOS ma poiché non è ... – albertamg

+1

NSPointerArray è disponibile su iOS 6 e versioni successive. – quellish

2

Scrivi te una classe SparseArray utilizzando un NSMutableDictionary sottostante. Qualcosa di simile (codice minimo, appena testato, ma dovrebbe darti l'idea).

@interface SparseArray : NSObject { 

@private 
    NSMutableDictionary* _dict; 
    int count; 
} 

-(SparseArray*)initWithCapacity:(NSUInteger)anInt; 
-(id)objectAtIndex:(int)anIndex; 
-(void)insertObject:(id)anObject atIndex:(int)anIndex; 
- (void)removeObjectAtIndex:(int)anIndex; 
-(int)count; 

@implementation SparseArray 

-(SparseArray*)initWithCapacity:(NSUInteger)anInt { 

    if ((self = [super init])) { 
    _dict = [[NSMutableDictionary dictionaryWithCapacity:anInt] retain]; 
    count = 0; 

    } 
    return self; 
} 

-(id)objectAtIndex:(int)anIndex { 

    NSNumber* key = [NSNumber numberWithInt:anIndex]; 
    id object = [_dict objectForKey:key]; 
    return object; 
} 

-(void)insertObject:(id)anObject atIndex:(int)anIndex { 

    NSNumber* key = [NSNumber numberWithInt:anIndex]; 
    [_dict setObject:anObject forKey:key]; 
    count++; 

} 

- (void)removeObjectAtIndex:(int)anIndex { 

    NSNumber* key = [NSNumber numberWithInt:anIndex]; 
    id object = [_dict objectForKey:key]; 
    if (object) { 
    [_dict removeObjectForKey:key]; 
    count--; 
    } 
} 

-(int)count { 

    return count; 
} 

-(void)dealloc { 

    [_dict release]; 
    [super dealloc]; 
} 

@end 
+2

Sfortunatamente, questo oggetto non supporta l'enumerazione veloce. Anche se lo si fosse aggiunto adottando 'NSFastEnumeration', l'implementazione sarebbe stata molto inefficiente o non avrebbe garantito che l'enumerazione sarebbe stata ordinata (come ci si aspetterebbe da un oggetto array). – jhabbott