C++面向对象-5


派生类的构造函数

attention:

  • 在创建一个派生类的时候,系统会先创建一个基类。
  • 派生类会吸收基类的全部成员,但不包括构造函数和析构函数。
  • 派生类在调用自己的构造函数之前,会先调用基类的构造函数。
#include<iostream>
using namespace std;

class Clock
{
    private:
        int h;
        int m;
        int s;
    public:
        Clock()
        {
            cout<<"Clock's consturctor called !"<<endl;
        } 
};

class AlarmClock:public Clock
{
    private:
        int ah;
        int am;
        int as;
    public:
        AlarmClock()
        {
            cout<<"AlarmClock's constructor called!"<<endl;
        }
};

int main()
{
    AlarmClock A;
    return 0;
}


当基类的构造函数带参的时候,派生类的构造函数应该这么定义:
派生类狗制造函数名字(总形参表列):基类构造函数(实参表类) //注意这里基类的构造函数用了是实际参数

一但基类中有带参数的构造函数,派生类则必须有显式传参的派生类构造函数,来实现基类中参数的传递,完成初始化工作

#include<iostream>
using namespace std;

class Clock
{
    private:
        int h;
        int m;
        int s;
    public:
        Clock()
        {
            cout<<"Clock's constructor called"<<endl; 
        }
        Clock(int h,int m,int s)
        {
            cout<<"Clock's consturctor with paramter called !"<<endl;
        } 
};

class AlarmClock:public Clock
{
    private:
        int ah;
        int am;
        int as;
    public:
        AlarmClock()
        {
            cout<<"AlarmClock's constructor called!"<<endl;    
        } 
        AlarmClock(int h,int m,int s):Clock(h,m,s)
        {
            cout<<"AlarmClock's constructor with paramter called!"<<endl;
        }

};

int main()
{
    AlarmClock A; 
    AlarmClock B(20,47,55);
    return 0;
}

派生类的析构函数

构造函数调用顺序:基类->派生类
析构函数调用顺序:派生类->基类

#include<iostream>
using namespace std;

class Clock
{
    private:
        int h;
        int m;
        int s;
    public:
        Clock()
        {
            cout<<"Clock's consturctor called !"<<endl;
        }
        ~Clock()
        {
            cout<<"Clock's destructor called !"<<endl;    
        } 
};

class AlarmClock:public Clock
{
    private:
        int ah;
        int am;
        int as;
    public:
        AlarmClock()
        {
            cout<<"AlarmClock's constructor called !"<<endl;
        }
        ~AlarmClock()
        {
            cout<<"AlarmClock's destructor called !"<<endl;
        } 
};

int main()
{
    AlarmClock A;
    return 0;
}


虚基类,使用virtual进行声明

  • 虚继承的出现成为了解决多继承中二义性问题的一种方式

  • 如果一个派生类有多个直接基类,而这些直接基类又有一个共同的基类,则在最终的派生类中会保留该间接共同基类数据成员的多份同名成员,这时就产生了二义性问题。

#include<iostream>
using namespace std;

class grandfather
{
    public:
        int key;
};

class father_1:public grandfather 
{

};

class father_2:public grandfather
{
};

class grandson:public father_1,public father_2
{

};

int main()
{
    grandson A;
    A.key = 10; //[Error] 
    return 0;
} 

在继承的时候在继承类型public之前用virtual修饰一下

  • 虚基类并不是在声明基类时声明的,而是在声明派生类时,指定继承方式时声明的。

  • 为了保证虚基类在派生类中只继承一次,应当在该基类的所有直接派生类中声明为虚基类。否则仍然会出现对基类的多次继承。

#include<iostream>
#include<cstdio>
using namespace std;

class grandfather
{
    public:
        int key;
};

class father_1:virtual public grandfather 
{

};

class father_2:virtual public grandfather
{
};

class grandson:public father_1,public father_2
{

};

int main()
{
    grandson A;
    A.key = 10;
    printf("%d",A.key);
    return 0;
} 

https://www.cnblogs.com/yiranlaobaitu/p/3764422.html
https://blog.csdn.net/bxw1992/article/details/77726390



文章作者: ShanSan
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 ShanSan !
  目录