Как указывать дозу базового указателя в производном классе? - PullRequest
1 голос
/ 02 мая 2020

Как я знаю, мы могли бы использовать указатель базового класса для адресации и вызова виртуальных функций в производных классах, потому что указатель базового класса имеет более ограниченную область указателя. Но я просто хочу знать, как указатель базового класса знает, с чего начать в производном классе?

Например, для записи A, B и C у всех HAS есть собственные члены-данные, мы можем обсудить это выпуск в двух разных категориях 1. A, B & C все имеют свои виртуальные функции; 2. A, B & C имеют только свои собственные элементы данных без каких-либо виртуальных функций

class A {...};
class B {...};
class C : public A, public B {...};

C c;
B* b = &c

Внутри C, A следует поместить поверх B, так как указатель b знает, где начать адресацию в C?

1 Ответ

1 голос
/ 02 мая 2020

Компилятору известно расположение, поэтому он выдаст код, который вычислит адрес подобъекта B в C.

Давайте рассмотрим простой пример:

class A { int x; };
class B { int y; };
class C: public A, public B { };

B *get(C &c) {
    return &c;
}

В get компилятор должен вычислить, где B находится в C. Вот пример скомпилированного кода ( godbolt ):

get(C&):                              # @get(C&)
        lea     rax, [rdi + 4]
        ret

Это означает, что компилятор добавит 4 байта к адресу входного аргумента (c) и вернет это (добавляет 4, потому что sizeof(A) равно 4, и компилятор решил не добавлять никаких дополнительных заполнителей).

Обратите внимание, что если A пусто, то вполне вероятно, что адрес B совпадает с C. И если A не является пустым (имеет элементы данных c, не относящиеся к состоянию, или имеет виртуальные функции), то адрес B, скорее всего, будет отличаться. Но все это детали реализации, зависит от платформы ABI (Application Binary Interface).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...