2016-03-25 3 views
0

Я не знаю точно, как работает код. Как A c0 = новый C(); * даже работа? Как я могу сделать объект «A» с указателем «C»?Как работает наследование?

class A { 
public: 
    A() { print("Constructor of A"); } 
    virtual ~A() { print("Destructor of A"); } 
}; 

class B : public A { 
public: 
    B() { print("Constructor of B"); } 
    ~B() { print("Destructor of B"); } 
}; 

class C : public B { 
public: 
    C() { print("Constructor of C"); } 
    ~C() { print("Destructor of C"); } 
}; 

int main() { 
    print("A* = C"); 
    A* c0 = new C(); 
    delete c0; 

    print("B* = C"); 
    B* c1 = new C(); 
    delete c1; 

    print("C* = C"); 
    C* c2 = new C(); 
    delete c2; 

    return 0; 
} 

Я думал, что я понял, наследство давно, но теперь, когда мне нужно, чтобы использовать его, я просто заблудился в коде.

+0

'class C: public B' означает, что« C »является« B ». Кроме того, 'B' является' A', поэтому 'C' также является' A'. Поскольку 'C' является' A', неудивительно, что вы можете назначить его 'A *'. – nwp

+0

Ум ... Но в этом коде используются только очень простые, связанные с наследованием свойства детского сада, связанные с наследованием. Как можно «понять наследство», но «заблудиться» в этом? – AnT

ответ

1

С C наследует от B, который наследует от A, C косвенно наследует от A. Таким образом, каждый экземпляр C также является экземпляром A. Следовательно, значение типа C* может быть непосредственно преобразовано в значение типа A*.

1

Добро пожаловать на Inheritance !! Continuous иерархия Наследование говорит правду ..

************************************* 
A Base 
B Base + (Something) 
C Base + (Something) + (Something) 
************************************** 

Помните, как на картинке выше .. так что теперь вы можете видеть, что C содержит основание, которое абсолютно Сам по себе .. так, что работает для вас ..

0

Поскольку C является производным от A, тогда все объекты C являются (isA) A. Новый оператор создает C, а так как C "isA" A, он может быть назначен указателю A *.

При использовании A * указатель можно вызывать только функции, которые определены в классе А. (так как тип указателя является A)

Если у вас есть C * указатель на объект C, вы можете вызовите любую из функций из A, B или C. (Предполагая, что они являются общедоступными или защищены).

Если у вас есть виртуальная функция «F», и невиртуальная функция «г», определенный в каждом из классов, а также следующие задания:

A * пА = новый A; A * pAC = новый C; C * pC = новый C;

тогда

PA-> F() будет вызывать A :: F(); pA-> g() вызовет A :: g();

pAC-> f() вызовет A :: f(); pAC-> g() вызовет C :: g();

pC-> f() вызовет C :: f(); pC-> g() вызовет C :: g();

Обратите внимание, что реальная область интересов представлена ​​в примере pAC. Вызов виртуальной функции всегда вызывает реализацию фактического объекта. Вызов простой функции вызывает реализацию на основе типа указателя.

Смежные вопросы