Как заставить мое iPhone-приложение динамически загружать протоколы? - PullRequest
3 голосов
/ 14 февраля 2011

Я пишу реализацию RPC с прокси-объектами (подумайте NSDistantObject).При этом мы генерируем заголовочные файлы (как DTO: s, так и протоколы) непосредственно из реализации сервера.Я динамически создаю объекты во время выполнения, но я столкнулся с определенной проблемой.

Когда я сталкиваюсь с объектом, у меня есть имя в виде строки, и я выясняю, что с ним делать.Моя проблема возникает, когда я пытаюсь «запросить» систему о протоколе, который не используется нигде в коде.Файл заголовка есть, даже #import: ред.

Некоторые примеры ...

Это прекрасно работает:

Protocol *protocol = NSProtocolFromString(@"UIApplicationDelegate"); // Returns a protocol

Если я возьму один из моихсобственные протоколы и указывает, что мой делегат приложения должен соответствовать ему, он также работает без проблем:

@interface ApplicationDelegate : NSObject <UIApplicationDelegate, ACMyCustomProtocol> {

}

// Implementation...

Protocol *protocol = NSProtocolFromString(@"ACMyCustomProtocol"); // Returns a protocol

Но если я запрашиваю протокол, которому не соответствует ни один класс в моем проекте, я получаю nil:

Protocol *protocol = NSProtocolFromString(@"ACMyCustomProtocolNotMentionedAnywhere"); // Returns nil

Я попытался изменить конфигурацию сборки (полагал, что Xcode может лишить неиспользуемый код при сборке) без удачи.Также попробовал Protocol *objc_getProtocol(const char *name) без удачи.

Редактировать:

Я получил совет от доброго пользователя на форумах разработчиков, к сожалению, это, вероятно, означает, что я вышелУдачи.

Язык программирования Objective-C: протоколы

Протоколы, которые объявлены, но не используются (за исключением проверки типов, как описано ниже) aren 't представлены объектами протокола во время выполнения.

1 Ответ

4 голосов
/ 15 февраля 2011

Поскольку ваши протоколы #import ed, простого выполнения @protocol(MyProtocolName) где-то в скомпилированном коде должно быть достаточно, чтобы убедиться, что объект Protocol существует во время выполнения.Возможно, хороший способ сделать это - создать статический NSDictionary, который сопоставляет известные имена протоколов с Protocol объектами.По сути, вы будете переопределять NSProtocolFromString для ваших известных протоколов, но это гарантирует, что эти объекты протокола будут скомпилированы.То есть что-то вроде:

+ (Protocol)remoteProtocolForName:(NSString *)name
{
    static NSDictionary *dict = nil;
    if (!dict)
    {
        dict = [[NSDictionary alloc] initWithObjectsAndKeys:
                @protocol(Foo), @"Foo",
                ...];
    }
    return [dict objectForKey:name];
}

Теперь мне приходит в голову, что я не уверен, что вы можете хранить Protocol с в NSDictionary ...

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...