वहाँ एक शब्दकोश पर पुनरावृति करने के लिए एक रास्ता है?


200

मैं NSDictionariesएक ऐसी चीज़ के रूप में जानता हूँ जहाँ आपको एक keyपाने की आवश्यकता है value। लेकिन मैं सभी पर keysऔर valuesएक में कैसे पुनरावृत्ति कर सकता हूं NSDictionary, ताकि मुझे पता चले कि क्या कुंजी हैं, और क्या मूल्य हैं? मुझे पता है कि कुछ एक फॉर-इन-लूप कहा जाता है JavaScript। क्या इसमें भी कुछ ऐसा ही है Objective-C?


इस पोस्ट के लिए धन्यवाद। यदि Swiftसिंटैक्स में पुनरावृत्ति होती है, तो इस पोस्ट को देखें: stackoverflow.com/a/24111700/419348
AechoLiu

जवाबों:


323

हां, NSDictionaryतेज गणना का समर्थन करता है। उद्देश्य-सी 2.0 के साथ, आप यह कर सकते हैं:

// To print out all key-value pairs in the NSDictionary myDict
for(id key in myDict)
    NSLog(@"key=%@ value=%@", key, [myDict objectForKey:key]);

वैकल्पिक विधि (जिसका उपयोग आपको करना है यदि आप Mac OS X को पूर्व 10.5 पर लक्षित कर रहे हैं, लेकिन आप अभी भी 10.5 और iPhone पर उपयोग कर सकते हैं) का उपयोग करना है NSEnumerator:

NSEnumerator *enumerator = [myDict keyEnumerator];
id key;
// extra parens to suppress warning about using = instead of ==
while((key = [enumerator nextObject]))
    NSLog(@"key=%@ value=%@", key, [myDict objectForKey:key]);

2
ObjC आधुनिक वाक्य रचना: NSLog (@ "key =% @ value =% @", कुंजी, myDict [कुंजी]);
जियोवर

@Darthenius हाल ही में अनुकूलन के कारण, तेजी से गणना फिर से ब्लॉक-आधारित की तुलना में तेज है, कम से कम कुछ मामलों में। लेकिन अगर आपके द्वारा हल की जा रही समस्या आपको समवर्ती विकल्प का उपयोग करने की अनुमति देती है, तो ब्लॉक-आधारित दृष्टिकोण तेज हो सकता है।
ज़ेव आइज़ेनबर्ग

@ZevEisenberg मेरी पोस्ट का अंत देखें।
रोक स्ट्रनिसा

ओह, मैंने एक नए टैब में खोलने के लिए आपके लिंक को ऊपर, क्लिक किया, और यह भी नहीं देखा कि इसे किसने लिखा है या यह उसी पृष्ठ पर था। यदि आप अभी भी उपरोक्त टिप्पणी को संपादित कर सकते हैं, तो आप चाहते हैं, ताकि आलसी पाठकों को गलत विचार न आए।
ज़ेव ईसेनबर्ग

153

ब्लॉक कुंजी हर कुंजी के लिए लुकअप एल्गोरिथ्म चलाने से बचती है :

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

भले ही हैशटेबल केNSDictionary रूप में लागू किया गया हो (जिसका अर्थ है कि किसी तत्व को देखने की लागत है ), लुकअप अभी भी एक स्थिर कारक द्वारा आपके पुनरावृत्ति को धीमा कर देता हैO(1)

मेरे माप से पता चलता है कि dसंख्याओं के शब्दकोश के लिए ...

NSMutableDictionary* dict = [NSMutableDictionary dictionary];
for (int i = 0; i < 5000000; ++i) {
  NSNumber* value = @(i);
  dict[value.stringValue] = value;
}

... ब्लॉक दृष्टिकोण के साथ संख्याओं को सम्‍मिलित करें ...

__block int sum = 0;
[dict enumerateKeysAndObjectsUsingBlock:^(NSString* key, NSNumber* value, BOOL* stop) {
  sum += value.intValue;
}];

... पाश दृष्टिकोण के बजाय ...

int sum = 0;
for (NSString* key in dict)
  sum += [dict[key] intValue];

... लगभग 40% तेज है

संपादित करें : नया एसडीके (6.1+) लूप पुनरावृत्ति को अनुकूलित करता प्रतीत होता है, इसलिए लूप अप्रोच ब्लॉक के दृष्टिकोण से लगभग 20% तेज है , कम से कम ऊपर के साधारण मामले के लिए।


IOS 10/11 में क्या है, कौन सा तेज है?
सुपरटेकनेबॉफ 10

सुरुचिपूर्ण, इसे प्यार करो!
यवसलेबोर्ग

10

ब्लॉक एप्रोच का उपयोग करके यह पुनरावृत्ति है:

    NSDictionary *dict = @{@"key1":@1, @"key2":@2, @"key3":@3};

    [dict enumerateKeysAndObjectsUsingBlock:^(id key, id obj, BOOL *stop) {
        NSLog(@"%@->%@",key,obj);
        // Set stop to YES when you wanted to break the iteration.
    }];

स्वतः पूर्णता सेट करने के लिए बहुत तेज़ है, और आपको पुनरावृत्ति लिफाफा लिखने के बारे में चिंता करने की आवश्यकता नहीं है।


धन्यवाद .. अच्छा समाधान अगर आपको NSMutableDictionaryप्रक्रिया में
म्यूट
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.