Нет. -forwardInvocation:
используется как часть механизма пересылки сообщений. Не беспокойтесь о пересылке сообщений, так как на самом деле она используется только прокси-объектами, и велика вероятность, что вам никогда не понадобится ее использовать и вы будете знать, что вы ее используете.
-performSelector:
предполагает, что тип возвращаемого сообщения id
или совместим, поэтому это небезопасно, если оно используется для отправки сообщения, возвращаемый тип которого отличается (например, шире, чем указатель, такой как long long
, в 32-битных системах, или возвращается через другой регистр / адрес, например float
или большой struct
.)
Если вы хотите косвенно отправить подобное сообщение, вы можете создать экземпляр класса NSInvocation
, а затем отправить его -invoke
. Затем возвращаемое значение сохраняется в объекте вызова и может быть доступно через него. -forwardInvocation:
никогда не используется вами в этом сценарии.
Вообще говоря, если вы обнаружите, что используете -performSelector:
, вы, вероятно, имеете дело с антипаттерном. В этом случае вы пытаетесь отправить сообщение, о котором ClassA
официально не знает. Альтернативное решение - раскрыть эти частные методы.
Если у вас есть и ClassA
, и ClassB
, вы можете создать «частный» заголовок для ClassB
, который включает в себя частные методы, которые вы хотите использовать. Если кто-то другой (например, Apple) владеет ClassB
, вы имеете дело с недокументированными API-интерфейсами и, возможно, вам придется искать другой подход, поскольку Apple отклонит приложение, использующее такие API-интерфейсы.
Чтобы создать частный заголовок, войдите в Xcode и создайте новый файл заголовка. Назовите его как-нибудь вроде «ClassB + Internal.h» или «ClassB + PrivateMethodsForMeOnly.h». Относитесь к нему как к частному для вашего проекта - никто не сможет использовать его, если только они не являются коллегами (тот же подпроект, библиотека или компонент) с ClassB
. В этот новый заголовок добавьте следующее:
#import "ClassB.h" // so we get the original class definition
@interface ClassB (PrivateMethodsForMeOnly)
- (double)someMethod;
- (const struct low_level_c_type_t)otherMethod:(int)i;
// etc. etc. etc.
@end
И в ClassA.m
(не ClassA.h
, если вы не хотите предоставлять эти методы всем, кто использует ClassA
!) Добавьте следующую строку в свой раздел include:
#import "ClassB+PrivateMethodsForMeOnly.h"
ClassA
после этого получит доступ к этим методам в новой категории.
person
Jonathan Grynspan
schedule
07.07.2012