2011-04-10 2 views

ответ

80

Это аннотации параметров метода и возвращаемых значений, которые были использованы распределенными объектами. Я говорю, были, потому что, видимо, их в документации Apple больше нет. Раньше был раздел «Удаленные сообщения» в документе «Язык программирования Objective-C», на который все еще ссылается документ «Распространенные объекты».

  • в: аргумента является только входным аргументом и не будет ссылаться позже
  • из: аргумент является только выходной аргумент, используемый для возвращения значения по ссылке
  • INOUT: аргумент как входным и выходным аргументом
  • Const: (указатель) аргумент константа
  • bycopy: вместо того, чтобы использовать прокси/NSDistantObject, передать или вернуть копию объекта
  • ByRef: использования прокси-объекта (по умолчанию)
+0

Большое спасибо! В частности, документация больше недоступна. Фактически, я искал документацию, но все ссылки были сломаны. – Eonil

+48

FWIW, Apple использовал 'inout' в новом' UIScrollViewDelegate' методе. ('targetContentOffset: (inout CGPoint *) targetContentOffset'. Так я пришел сюда, так или иначе. – Mazyod

+6

На самом деле я тоже. Если они могут использовать inout, почему, черт возьми, им нужно сделать что-то сложное, как сделать двойной указатель, чтобы получить ошибку? что они передают CGPOINT *, им не нужно указывать inout вообще. Это указатель. CGPOINT - это структура. Пока вы добавляете новый CGPOINT к адресу, указанному targetContentOffset, вы сделаете все правильно. –

0

Если кто-то наткнулся на это сообщение и имеет ту же путаницу, что и я, аргумент «in» также может быть ключевым словом, которое представляет собой быстрое перечисление. См. here для получения более подробной информации.

+0

Такая общая конструкция на других текущих языках, таких как Java и Python, но практически никогда не использовалась в Obj-C. Лично я склонен использовать blockEnumerators, когда мне это нужно, хотя это связано с гораздо большим количеством ввода текста ... IDK, я чувствую, что кто-то, читающий мой код, скорее всего мгновенно получит его таким образом. – ArtOfWarfare

22

Помимо распределенных объектов, одна из этих аннотаций, по-видимому, используется ARC. Я наткнулся на следующее в описании звоном о passing to an out parameter by writeback:

If the parameter is not an Objective-C method parameter marked out , then *p is read, and the result is written into the temporary with primitive semantics.

Это связано с методами, как - (BOOL)executeWithError:(out NSError **)error.

Игнорирование out ключевого слова, АРК имеет well-defined behavior of treating by-reference object passing as __autoreleasing, поэтому АРК рассматривает параметр error как имеющий тип NSError * __autoreleasing *. Если вы используете в противном случае квалифицированное переменную, ARC будет добавить переменную временного autoreleasing передать в функцию (для согласования):

Оригинальный код

NSError *error; 
[obj executeWithError:&error]; 

Pseudotransformed код

NSError * __strong error; 
NSError * __autoreleasing temp; 
temp = error; 
[obj executeWithError:&temp]; 
error = temp; 

С приведенным выше кодом строка temp = error была бы лишней, если бы мы как-то знали, что temp никогда не будет считаться. Здесь вступает в действие аннотация out.В цитируемом описании, если отсутствует out, компилятор должен добавить строку temp = error, но если он содержит out, он может исключить строку и сделать код немного меньше/быстрее. С out преобразованный код становится:

NSError * __strong error; 
NSError * __autoreleasing temp; 
[obj executeWithError:&temp]; 
error = temp; 

Конечно, если вы беспокоитесь о том, что бинарный размер и скорость, вы должны просто закодировать следующее:

NSError * __autoreleasing error; 
[obj executeWithError:&error]; 

Вполне возможно, что эти аннотации используются в других местах во всем компиляторе и во время выполнения и могут использоваться в будущем в других местах. Лично мне нравится использовать out как подсказку для других разработчиков, что я не буду читать значение.

+0

* Оригинальный код * кажется, отсутствует один адрес-оператора. 'executeWithError: & error];' – Eonil

+0

Спасибо @Eonil, исправлено! –

+0

@BrianNickel so (out NSError **) и (NSError * __autoreleasing *) одинаковы? – denis631

Смежные вопросы