Подтвердить что ты не робот

Objective-C: Зачем проверять nil перед ответомToSelector:?

Я видел код вроде:

if (delegate != nil && [delegate respondsToSelector:@selector(doSomething)]) ...

Но, отправляя сообщение в nil, просто возвращает nil (который оценивается как NO), поэтому почему бы просто не сделать:

if ([delegate respondsToSelector:@selector(doSomething)]) ...

Быстрее ли это, если delegate == nil? В любом случае, я предпочитаю, чтобы последние вызывали у него меньше кода.

И, less лучше, чем more. Каждый Unix-профессионал знает об этом.

4b9b3361

Ответ 1

objc_msgSend, функция, используемая для отправки динамических сообщений в Objective-C, сразу проверяет первый аргумент (приемник сообщений) и возвращает, если он == nil. Таким образом, единственное накладное сообщение nil-сообщений - это динамически связанный вызов функции библиотеки, который немного дороже, чем вызов функции "внутри двоичной" функции. В целом, один подход более эффективен, чем другой? Условные условные операторы обычно требуют дополнительного разветвления, поэтому ответ неопределен, не глядя на код, который генерирует компилятор, но более важно профилировать запущенную программу. Преждевременная оптимизация - это Bad Thing ™, но я поздравляю вас с фактическим рассмотрением эффективности и опросом таких "идиом".

Ответ 2

Вы правы. Это технически лишние накладные расходы в Obj-C, так как любое сообщение, отправленное в nil, автоматически вернет nil. Однако, если вы проигнорируете вызов respondsToSelector:, сначала проверив, есть ли он nil, вы пропустите служебные данные вызова respondsToSelector:. Так что это будет быстрее, но насколько я не уверен.

Ответ 3

Здесь есть синтаксическая проблема: если вы отправляете -ответчикToSelector на объект nil, он всегда будет возвращать нуль. Вот почему вы так поступили бы.