Все это может быть довольно много для начинающего, чтобы понять. Итак, начнем с синтаксиса ObjectiveC:
Свойство @property (readonly) void *data;
предоставляет интерфейсы, которые говорят, что должен быть метод типа - (void *)data
, что означает метод экземпляра, возвращающий указатель void
. Пустой указатель является указателем на что-либо.
В этом случае ObjectiveC является чем-то вроде чистого C на уровень глубже. Я не буду проверять точное преобразование, но поскольку в C нет методов, все это делается с помощью функций или даже указателей на функции. Так что где-то там должна быть функция (скажем, имя этого класса MyDataClass
)
void *myDataClass_data(MyDataClass *self) { return self->_data; } // Or whatever the implementation is
Так что под капотом ничего интересного не происходит. Все это просто возвращает позицию в памяти без какой-либо дополнительной информации о том, что должно быть там. Вы как разработчик должны знать и интерпретировать это. С C (или ObjectiveC) это очень просто. Несколько примеров:
char *aString = (char *)myDataClass.data; // A pure C string. Expected to be null terminated
int *arrayOfIntegers = (int *)myDataClass.data; // An array of integers
int thirdItem = arrayOfIntegers[2];
MyDataClass *nextItem = (MyDataClass *)myDataClass.data; // A pointer to another instance
for(MyDataClass *iterator = myDataClass; iterator != nil; iterator = (MyDataClass *)iterator.data) {}
Надеюсь, вы поняли картину. Дело в том, что C, а затем и ObjectiveC очень небезопасны, когда речь идет о типах данных. Вы можете конвертировать что угодно во что угодно, и вы скомпилируете. Проблема в том, что произойдет во время выполнения.
При взгляде на Свифта все становится намного безопаснее, и вы не можете просто сказать что-то вроде let integer: Int = myDataClass as Int
. Вы можете принудительно разыграть его, и он рухнет. Или вы можете сделать дополнительный бросок, и он вернет nil
.
Так что после перехода из C / ObjectiveC вы получите небезопасный изменяемый необработанный указатель. Это означает, что он получил место в памяти, не имея представления о том, что это такое и как его использовать. Вы можете попытаться преобразовать его во что угодно, но это небезопасно , поскольку оно игнорирует все проверки типов. Это изменяемый , вероятно, потому что данные, которые он содержит, могут быть изменены в любой момент времени любой системой. Это raw , так как он не содержит никакой дополнительной информации (как будто это строка). И это указатель , потому что он указывает только на позицию в памяти.
(Все фрагменты являются символическими для объяснения того, что происходит под капотом. Пожалуйста, не воспринимайте их буквально)