" писал(а):Инициализация - это, прежде всего, выделение памяти под объкт. А выделение памяти и внесение изменений в таблицу - это разные вещи.
Я понял источник нашего непонимания. Он в том, что под инициализацией ты видишь выделение памяти. На самом деле инициализация - это процесс первоначальной (инициализирующей) простановки данных в объект. Инициализация не имеет отношения к выделению памяти. Эти два процесса можно разнести, например, воспользовавшись третьей формой оператора new.
Кстати, я тут перечитал статью, и понял, что вынужден извиниться перед Аланом Голубом, точнее даже не перед ним, так как во всём виноват переводчик. Я, расплёвываясь в разные стороны от досады, окончил читать статью вот на этой фразе.
" писал(а):
... и указатель в таблице виртуальной функции переписывается
Именно эта фраза и возмутила меня до глубины души, так как таблицы неизменяема.
Огромный респект переводчику. Текст на самом деле должен быть следующим, тогда он обретает смысл:
" писал(а):
... и указатель на таблицу виртуальных функций переписывается так, чтобы он указывал на таблицу производного класса.
Там ещё следует исправить несколько ляпов, который также остаются на совести переводчика. Например текст, прямо перед предыдущим текстом:
" писал(а):
которая добавляет таблицу этой виртуальной функции к своей таблице и выполняется.
Следует перефразировать целиком.
" писал(а):
которая записывает в указатель на таблицу виртуальных функций адрес своей таблицы и выполняется.
После этой поправки статья целиком повторяет то, что я описал в своём посте две страницы назад, ещё до того, как узнал об этом писателе. То есть мы возвращаемся к выведенной ранее последовательности вызовов:
Код: Выделить всё
vptr = &Table(A)
A()
vptr = &Table(B)
B()
vptr = &Table(C)
C()
Теперь, дорогой
Airhand, укажи мне, плиз, где ты нашёл в статье упоминание о том, что указатель на таблицу перезаписывается лишь после выполнения тела конструктора?
Далее по приведённому коду.
" писал(а):
_vtab *_vtable; // Генерируемое компилятором поле данных.
Ха-ха, уже не возникает вопросов почему первые четыре байта в объекте - это указатель на таблицу виртуальных функций? Почему же по-прежнему критикуешь мою программу?
" писал(а):
_employee__ctor( employee *this ) // Конструктор по умолчанию, генерируемый
{ // компилятором.
_storable_ctor(); // Базовые классы инициализируются
// в первую очередь.
_vtable = _employee_vtable; // Создается таблица виртуальных функций.
}
Порядок вызова выдумал ты. На самом деле он обратный, это доказывает моя программа и этому нет противоречий в статье.
А вот это вообще шедевр.
" писал(а):
_vtable = _employee_vtable; // Создается таблица виртуальных функций.
Я же тебе ещё раньше написал, чтобы ты писал побольше кода и комментариев лично от себя. Я бы тебе давно указал в каком именно месте ты неверно используешь терминологию или просто ошибаешься и наш спор даным давно бы завершился. Открою тебе секрет. В той строке, напротив который ты написал "Создаётся таблица" на самом деле таблица не создаётся. В этой строке происходит ПРИСВАИВАНИЕ УКАЗАТЕЛЯ НА ТАБЛИЦУ. Это абсолютно не одно и то же. Вот небольшой ликбез с комментариями.
Код: Выделить всё
int i; // Создание переменной
int *p; // Создание указателя
p = &i; // Установка указателя p на область памяти i
То же самое касается и нашего случая. На момент выполнения квотированной строки и указатель, и таблица уже созданы. Указатель - на этапе создания объекта. Таблица - вообще до входа в main на этапе загрузки исполняемого файла в память. В указанной же строке происходит ПРИСВАИВАНИЕ УКАЗАТЕЛЯ на таблицу, а не СОЗДАНИЕ таблицы. Во время работы всей программы эта таблица не меняется.
--------------------------------------------------------------------------------
Добавлено сообщение
--------------------------------------------------------------------------------
[offtop]
Hawk, рад видеть тебя. Где пропадал так долго? [/offtop]