Информация об изменениях

Сообщение Re[3]: Как удаляется vptr? от 10.04.2023 20:29

Изменено 10.04.2023 20:30 rg45

Re[3]: Как удаляется vptr?
Здравствуйте, avovana, Вы писали:

A>То есть правильно здесь представили что vptr лишь у базового. И наследники как-будто бы его наследуют?


На уровне идеи это можно представлять себе так. Нужно только помнить, что ни сам vptr, ни таблица виртуальных функций, на которую он указывает, недоступны программисту. Эти структуры данных полностью управляются компилятором, и то, как они устроены, где располагаются, в какой момент и в какой области выделяется память под таблицы виртуальных функций и в какой момент эта память освобождается — об этом знает только компилятор и в разных компиляторах это может быть устроено по-разному.

A>
A>class Base
A>{
A>public:
A>    FunctionPointer* __vptr;
A>    virtual void function1() {};
A>    virtual void function2() {};
A>};

 
A>class D1: public Base
A>{
A>public:
A>    virtual void function1() {};
A>};
 
A>class D2: public Base
A>{
A>public:
A>    virtual void function2() {};
A>};
A>

A>https://radioprog.ru/post/1279
A>Тогда в случае не виртуального деструктора у базового класса как в топикстарте — "vptr не будет утекать". Интервьюер всё пытался понять от меня — будет ли он утекать или нет) Просто если у каждого он свой:
A>у base
A>у derived
A>то ведь если
A>
A>Base *obj = new Derived // без virtual dtor
A>delete obj
A>

A>То что будет с Derived vptr?

Я думаю, что по этой ссылке просто картинка неудачная, хотя на словах все написано правильно:

Компилятор также добавляет член скрытого указателя к самому базовому классу, который использует виртуальные функции. Хотя компилятор делает это автоматически, покажем в следующем примере, куда он добавляется:

Смысл же в том, чтоб, имея один только указатель на Base, мы могли бы найти таблицы виртуальных функций любых производных классов. Как это можно сделать, если дополнительная информация, необходимая для поиска таблиц, (которую мы условно называем vptr), не будет доступна через Base?

Ну и главное, данный сценарий порождает неопределенное поведение. Что будет дальше, не знает никто! Вот так и нужно было ответить.
Re[3]: Как удаляется vptr?
Здравствуйте, avovana, Вы писали:

A>То есть правильно здесь представили что vptr лишь у базового. И наследники как-будто бы его наследуют?


На уровне идеи это можно представлять себе так. Нужно только помнить, что ни сам vptr, ни таблица виртуальных функций, на которую он указывает, не доступны программисту. Эти структуры данных полностью управляются компилятором, и то, как они устроены, где располагаются, в какой момент и в какой области выделяется память под таблицы виртуальных функций и в какой момент эта память освобождается — об этом знает только компилятор и в разных компиляторах это может быть устроено по-разному.

A>
A>class Base
A>{
A>public:
A>    FunctionPointer* __vptr;
A>    virtual void function1() {};
A>    virtual void function2() {};
A>};

 
A>class D1: public Base
A>{
A>public:
A>    virtual void function1() {};
A>};
 
A>class D2: public Base
A>{
A>public:
A>    virtual void function2() {};
A>};
A>

A>https://radioprog.ru/post/1279
A>Тогда в случае не виртуального деструктора у базового класса как в топикстарте — "vptr не будет утекать". Интервьюер всё пытался понять от меня — будет ли он утекать или нет) Просто если у каждого он свой:
A>у base
A>у derived
A>то ведь если
A>
A>Base *obj = new Derived // без virtual dtor
A>delete obj
A>

A>То что будет с Derived vptr?

Я думаю, что по этой ссылке просто картинка неудачная, хотя на словах все написано правильно:

Компилятор также добавляет член скрытого указателя к самому базовому классу, который использует виртуальные функции. Хотя компилятор делает это автоматически, покажем в следующем примере, куда он добавляется:

Смысл же в том, чтоб, имея один только указатель на Base, мы могли бы найти таблицы виртуальных функций любых производных классов. Как это можно сделать, если дополнительная информация, необходимая для поиска таблиц, (которую мы условно называем vptr), не будет доступна через Base?

Ну и главное, данный сценарий порождает неопределенное поведение. Что будет дальше, не знает никто! Вот так и нужно было ответить.