この質問は古く、物事は変わっていませんが、受け入れられた答えは正しくありません。
enumerateObjectsUsingBlock
APIは、取って代わるものではありませんでしたfor-in
が、全く異なるユースケースのために:
- これにより、任意の非ローカルロジックを適用できます。つまり、配列で使用するためにブロックが何を行うかを知る必要はありません。
- 大規模なコレクションまたは大量の計算の同時列挙(
withOptions:
パラメーターを使用)
Fast Enumeration with for-in
は、コレクションを列挙する慣用的な方法です。
高速列挙は、コードの簡潔さ、読みやすさ、および不自然に高速化する追加の最適化の恩恵を受けます。古いCのforループよりも高速です!
クイックテストの結果、2014年のiOS 7は、enumerateObjectsUsingBlock
for-inよりも一貫して700%遅い(100アイテムの配列の1mmの反復に基づく)。
ここでパフォーマンスは実際の懸念事項ですか?
間違いなく、まれな例外があります。
ポイントは、使用にはほとんどメリットがあることを実証することであるenumerateObjectsUsingBlock:
以上は、for-in
、本当に正当な理由なし。コードが読みやすくなることはありません...またはより速く...またはスレッドセーフ。(別の一般的な誤解)。
選択は個人の好みに帰着します。私にとっては、慣用的で読みやすいオプションが優先されます。この場合、それはを使用しfor-in
た高速列挙です。
基準:
NSMutableArray *arr = [NSMutableArray array];
for (int i = 0; i < 100; i++) {
arr[i] = [NSString stringWithFormat:@"%d", i];
}
int i;
__block NSUInteger length;
i = 1000 * 1000;
uint64_t a1 = mach_absolute_time();
while (--i > 0) {
for (NSString *s in arr) {
length = s.length;
}
}
NSLog(@"For-in %llu", mach_absolute_time()-a1);
i = 1000 * 1000;
uint64_t b1 = mach_absolute_time();
while (--i > 0) {
[arr enumerateObjectsUsingBlock:^(NSString *s, NSUInteger idx, BOOL *stop) {
length = s.length;
}];
}
NSLog(@"Enum %llu", mach_absolute_time()-b1);
結果:
2014-06-11 14:37:47.717 Test[57483:60b] For-in 1087754062
2014-06-11 14:37:55.492 Test[57483:60b] Enum 7775447746