Странно для циклов, с которыми я не знаком: "for (id * in *)"
Я прошу прощения, если этот вопрос чрезвычайно прост, но я погуглил как сумасшедший и не могу найти подходящего объяснения, что это такое.
for (id line in self.lines){
[linesCopy addObject:[line copyWithZone:zone]];
}
Я только учусь Objective-C, и это форма for
петля, которую я никогда раньше не видел. Я знаком с простым
for (int x = 1, x < 10, x++)
стиль for
петля.
4 ответа
Из основных компетенций Какао: Перечисление:
Быстрое перечисление
Несколько классов Какао, включая классы коллекции, принимают
NSFastEnumeration
протокол. Он используется для извлечения элементов, содержащихся в экземпляре, с использованием синтаксиса, аналогичного синтаксису стандартного цикла C for, как показано в следующем примере:NSArray *anArray = // get an array; for (id element in anArray) { /* code that acts on the element */ }
Как следует из названия, быстрое перечисление более эффективно, чем другие формы перечисления.
Если ты не знал, id
является типом Objective C, который в основном означает "указатель на любой объект Objective C". Обратите внимание, что указатель id
встроен в него; Вы обычно не хотите говорить id *
,
Если вы ожидаете элементы anArray
скажем, определенного класса MyObject
, вы можете использовать это вместо:
for (MyObject *element in anArray) {
/* code that acts on the element */
}
Однако ни компилятор, ни среда выполнения не проверят, что элементы действительно являются экземплярами MyObject
, Если элемент anArray
не является примером MyObject
вы, вероятно, в конечном итоге попытаетесь отправить ему сообщение, которое он не понимает, и получите исключение, не распознаваемое селектором.
Это называется forin
цикл, также называемый быстрым перечислением. В основном, синтаксис:
for (SomeObjectIAmExpecting *localVariableName in anArrayOfObjects)
{
if (![localVariableName isKindOfClass:[SomeObjectIAmExpecting class]]) continue; //To avoid errors.
//do something to them
}
Это утверждение, которое можно использовать с классами, которые соответствуют NSFastEnumeration
протокол. Когда у вас есть это, руководство по программированию Objective-C предлагает вам его использовать. Посмотрите здесь. Это способ перебора коллекции без традиционного for (int i = 0; i < length; ++i)
синтаксис.
Имейте в виду, что он обычно не поддерживает удаление и вставку элементов во время итерации по этому пути (также с использованием обычного for
Зацикливайтесь на индексах нужно в любом случае позаботиться).
В основном все стандартные коллекции поддерживают этот способ итерации.
Это сокращенный эквивалент этой распространенной формы:
for (int i = 0; i < [self.lines count]; i++) {
id line = [self.lines objectAtIndex:i];
// ...
}
Это настолько распространенная идиома зацикливания (обход некоторой коллекции, массива, набора и т. Д. За раз), что она превращается в сокращенную форму, такую как эта, называемая "быстрое перечисление".
Фактически, в своей внутренней реализации, это на самом деле немного быстрее, чем делать это самостоятельно, поэтому предпочтительнее как для ясности, так и для производительности.