TObject: ClassName, Pointer, vmtClassName |
Автор megabax | |||
03.08.2009 г. | |||
TObject (ClassName, Pointer, vmtClassName)Сегодня мы изучим некоторые методы класса TObject. Начнем с ClassName. Эта функция возвращает имя класса. Для иллюстрации ее работы рассмотрим пример:
*Испытав пример, мы убедился, что даже если у нас есть переменна родительского класса и мы присваиваем ей объект дочернего класса, то все равно, функция ClassName корректно вернет имя того класса, экземпляром которого фактически является данный объект. А теперь, давайте ради интереса посмотрим, как же реализована данная функция:
Сразу бросается в глаза {$IFDEF PUREPASCAL}. Это директива препроцессора. $IFDEF означает условную компиляцию. В зависимости от установленной опции PUREPASCAL компилятор компилирует либо строку Result := PShortString(PPointer(Integer(Self) + vmtClassName)^)^; либо вставку на ассемблере (иными словами, непосредственно в машинных командах), которая делает в принципе, тоже самое, но гораздо быстрее. Кстати по умолчанию PUREPASCAL отключена, то есть, стандартные модули скомпилированы в режиме когда выполняются ассемблерные вставки, тоесть, в оптимизированном на скорость режим. В настройках Delphi 7 нет опций, соответствующих данной директиве. Правда, ее можно включить вручную, для это войдем в меню "Options"*. В открывшемся окне перейдем на закладку Directories/Conditionals и в Conditional defines ручками впишем директиву PUREPASCAL*. Правда, для того, что бы перекомпилировать стандартные модули, нужно сильно извратится, и сейчас мы это делать не будем, зачем же нам замедлять работу программы? Теперь разберемся, что же делает выражение Result := PShortString(PPointer(Integer(Self) + vmtClassName)^)^; И так, функция возвращает значение, расположенное по адресу PShortString(PPointer(Integer(Self) + vmtClassName)^). Сам этот адрес у нас берется из адреса, хранящемся по адресу PPointer(Integer(Self) + vmtClassName)^. Выражение PShortString означает, что значение нужно привести к типу "указатель на короткую строку". Иными словами, по указанному адресу у нас расположен адрес, где находиться строка. Если данное выражение "сломало вам мозг", давайте попробуем представить память компьютера как длинную предлинную дорогу по бокам которой через равные промежутки стоят столбы. Возле каждого столба стоит шкафчик с надписью "Информация". Каждый столб, и соответственно, шкафчик, пронумерован. В шкафчике может лежать не только какая то полезная информация, но так же номер другого шкафчика, где лежит искомая информация. А может лежат например, сообщение, что искомая информация находится через три шкафчика от шкафчика с номером 123. А может вообще находиться какая нибудь дикая инструкция, что нужно пройти такое то число ящиков и дальше выполнять инструкцию, хранящуюся в том ящика, до которого вы дошли. Грубо говоря, у нас есть переменная vmtClassName - очередной шкафчик, которая хранит смещения относительно адреса объекта (это уже другой шкафчик). Как бы данное выражение говорит нам: "от шкафчика self пройдите vmtClassName шкафчиков вперед". Вы идете к этому шкафчику и находите там информацию куда идти дальше. Но это еще не все. По указанному адресу находиться номер следующего шкафчика. Вот у нас и получился адрес адреса (двойной символ ^).
Скриншоты, помеченные знаком * , являются цитатами и иллюстрациями программного продукта "Delphi", авторское право на который принадлежит "Borland Software Corporation".
|
|||
Последнее обновление ( 22.05.2013 г. ) |
« След. | Пред. » |
---|