Objektif-C'deki her döngü için NSMutable sözlüğüne erişim


268

Objective-C'de değişebilir sözlük anahtarlarına ve değerlerine erişmekte zorluk yaşıyorum.

Varsayalım:

NSMutableDictionary *xyz=[[NSMutableDictionary alloc] init];

Anahtarları ve değerleri ayarlayabilirim. Şimdi, her bir tuşa ve değere erişmek istiyorum, ancak ayarlanan anahtar sayısını bilmiyorum.

PHP'de çok kolay, aşağıdaki gibi bir şey:

foreach ($xyz as $key => $value)

Objective-C'de nasıl mümkün olabilir?

Yanıtlar:


662
for (NSString* key in xyz) {
    id value = xyz[key];
    // do stuff
}

Bu, NSFastEnumeration protokolüne (10.5+ ve iOS'ta kullanılabilir) uyan her sınıf için geçerlidir, ancak NSDictionarydeğerler yerine anahtarları numaralandırmanıza izin veren birkaç koleksiyondan biridir. Onun hakkında senin önermek hızlı numaralandırma içinde Konu Programlama Koleksiyonu .

Oh, ancak eklemeliyim ki ASLA bir koleksiyonu üzerinde numaralandırırken modifiye etmemelisiniz .


4
Merak ediyordum, olmalıydı: için ([xyz allKeys] NSString * anahtar)) ?? Yoksa gerçekten önemli değil.
— FlowUI. SimpleUITesting.com

6
@ user76859403 Bir sözlüğü numaralandırmak aslında anahtarları numaralandırır. for (NSString* key in [xyz allKeys])kavramsal olarak aynı şeydir.
— zneak

Tuşları numaralandırırken sözlüğü değiştirmeniz gerekiyorsa [xyz allKeys] kullanın. Cevabımı aşağıda görebilirsiniz.
— Brody Robertson

Bu döngü her zaman aynı sıraya dönüyor mu? Yoksa TableView bölümleri için kullanmak için başka bir yola mı ihtiyacımız var?
— ymutlu

1
@ymutlu, Kakao sözlükleri sıralanmamış. Bu, yinelendikleri sırayı değiştirdiğinizde değişebileceği anlamına gelir.
— zneak

98

Sadece blokları kullanarak değerleri ve anahtarları numaralandırmak için 10.6+ seçeneğini dışarıda bırakmamak için ...

[dict enumerateKeysAndObjectsUsingBlock:^(id key, id object, BOOL *stop) {
    NSLog(@"%@ = %@", key, object);
}];

İşlemlerin aynı anda gerçekleşmesini istiyorsanız:

[dict enumerateKeysAndObjectsWithOptions:NSEnumerationConcurrent
                              usingBlock:^(id key, id object, BOOL *stop) {
    NSLog(@"%@ = %@", key, object);
}];

2
Bir sözlükte numaralandırmanın 3 farklı yolu. . . heh, bu bana VB'nin 7 farklı türde döngüye sahip olduğu "En garip Dil Özelliği" cevabını hatırlatıyor.
— dreamlax

3
Şey ... objectEnumerator 1994 yılında, for (... in ...) 2006 yılında eklendi ve Bloklar 2009 yılında eklendi. Numaralandırmanın blok şekli doğal serpinti.
— bbum

Bu daha hızlı standardından daha görünüyor içinde ... için yapı: oneofthesedaysblog.com/block-vs-for-in-objective-c-enumeration
— lkraider

1
@lkraider, aslında blok tabanlı numaralandırmayı yapı için for ... değil, eski bir for döngüsü ile karşılaştıran bu yazıya yorum yaptım.
— Quinn Taylor

Ne *stopiçin? Bunu nasıl kullanıyorsunuz? Referans var mı?
— borisdiakur

13

Numaralandırırken sözlüğü değiştirmeniz gerekiyorsa :

for (NSString* key in xyz.allKeys) {
    [xyz setValue:[NSNumber numberWithBool:YES] forKey:key];
}

Bunun nedeni, allKeysanahtarların bir kopyasını döndürmektir. Bu yüzden sözlüğü değiştirmek güvenlidir.
— Honghao Zhang

5

Bir sözlüğü numaralandırmanın en kolay yolu

for (NSString *key in tDictionary.keyEnumerator) 
{
    //do something here;
}

nerede tDictionaryolduğunu NSDictionaryya da NSMutableDictionarysen yineleme istiyorum.



2

10.5 ve iPhone OS'de hızlı numaralandırma eklendi ve sadece sözdizimsel şeker değil, önemli ölçüde daha hızlı. Eski çalışma zamanını (yani 10.4 ve geri) hedeflemeniz gerekiyorsa, eski numaralandırma yöntemini kullanmanız gerekir:

NSDictionary *myDict = ... some keys and values ...
NSEnumerator *keyEnum = [myDict keyEnumerator];
id key;

while ((key = [keyEnum nextObject]))
{
    id value = [myDict objectForKey:key];
    ... do work with "value" ...
}

Sayıcı nesnesini serbest bırakmazsınız ve sıfırlayamazsınız. Baştan başlamak istiyorsanız, sözlükten yeni bir numaralandırıcı nesnesi istemeniz gerekir.


1

Sen kullanabilirsiniz -[NSDictionary allKeys]içinden tüm anahtarları ve döngü erişmek için.


2
Doğru, ancak bu, özellikle çok sayıda tuşa sahip sözlükler için oldukça israflı olabilen ekstra bir otomatik yayın dizisi oluşturur.
— Quinn Taylor
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.