Возможно создать класс в Objective-C ++, который имеет поле, которое является указателем на интерфейс Objective-C (внутри .h
файл ) ?
Чтобы немного уточнить, я создал один интерфейс Objective C:
// Our platform independent class
@interface LoggerDelegate : NSObject<SomeDelegate>
@end
Я могу создать это внутри .mm
файл, и он работает, но он предназначен для глобальной переменной, и мне не разрешено изменять его область. Так что я хотел бы использовать его внутри Logger.h
:
class Logger {
public:
private:
LoggerDelegate* _ptr; //<--- pointer to the Objective-C interface
};
Когда я определяю свой интерфейс внутри Logger.mm
оно работает. Но возможно ли объединить код Objective-C ++ из Objective-C и C ++ внутри .h
файлы? Или это возможно только в .mm
файлы?
Objective-C использования .h
заголовки и .m
файлы реализации. Вам может не понадобиться последний в случае абстрактного интерфейса. Все эти файлы должны соответствовать синтаксису Objective C:
.h
или же .m
; это будет признано, потому что Цель C является расширением языка C. class
или же template
) не будет распознаваться компилятором Objective-C. Objective-C ++ также использует .h
заголовки но .mm
файлы реализации. Оба должны соответствовать синтаксису Objective-C ++:
Стандарт С ++ использует заголовки (обычно .h
или же .hpp
) и файлы реализации (обычно .cc
или же .cpp
). Они должны использовать только элементы языка C ++. Элементы языка Objective-C и Objective-C ++, которые не принадлежат C ++, такие как, например, @interface
вызовет ошибки компиляции C ++.
Смешивание Objective-C и Objective-C ++: Если вы поделитесь заголовками (.h
) между Objective-C и Objective C ++ они должны будут соответствовать как Objective-C, так и Objective-C ++. Следовательно, заголовок может использовать только общий знаменатель между двумя языками, то есть языковые элементы Objective-C (и C).
Смешивание стандартного C ++ и целевого C / C ++: Вы можете комбинировать язык C ++ с конструкциями Objective-C или Objective-C ++ только в Objective-C ++ (так .mm
файлы, и в конце концов .h
если и только если не включен ни в один стандартный исходный код C ++ или Objective-C)
Вот почему вы можете использовать свой интерфейс Objective C в .mm
файл. Но вы не можете использовать его в .h
файл, который будет включен в код C ++.
Объектная модель и жизненный цикл стандарта C ++ и Objective-C / C ++ не совпадают. Это затрудняет взаимодействие. Например, класс C ++ не может наследоваться от класса Objective-C, а если класс Objective-C содержит объект C ++, строительство может быть сложно. И не существует языковой конструкции C ++, которая гарантированно была бы изначально совместима с Objective-C ++ @interface
или.
Можно управлять указателями с объектов C ++ на Objective-C ++ с помощью PIMPL идиома (также называется «непрозрачный указатель»). Эта блестящая статья от Фила Джордана объясняет, как это сделать, на примере, который вы можете легко использовать повторно.
Основная идея Фила Джордана — использовать заголовок, чтобы обернуть объект Objective-C ++ в стандартный класс C ++, используя указатель на неполный объект. Фил использует условную компиляцию умным способом, чтобы позволить использование того же самого .h
для межъязыковых целей:
#ifdef __OBJC__
@class XXXX; // if header used in Objective C++
#else
struct XXXX; // if header used in standard C++
#endif
class WrapperClass { // standard C++ class also recognuzed by Objective C++
XXXX *wrapped_objective_c_object_pointer;
public:
...// public interface for C++
};
Это гарантирует, что код C ++, включающий заголовок, никогда не сможет использовать указатель для выполнения каких-либо операций с обернутым объектом. Реализация класса оболочки C ++ будет предоставлена в виде .mm
файл, который осведомлен о семантике Objective C ++. Я настоятельно рекомендую вам прочитать статью, чтобы понять все детали этого решения.
Других решений пока нет …