#include<iostream>
using namespace std;
class B1
{
public:
B1()
{
cout << "call B1" << endl;
}
};
class V1 : public B1
{
public:
V1()
{
cout << "call V1" << endl;
}
~V1()
{
cout << "call ~V1" << endl;
}
};
class D1 : virtual public V1
{
public:
D1()
{
cout << "call D1" << endl;
}
~D1()
{
cout << "call ~D1" << endl;
}
};
class B2
{
public:
B2()
{
cout << "call B2" << endl;
}
~B2()
{
cout << "call ~B2" << endl;
}
};
class B3
{
public:
B3()
{
cout << "call B3" << endl;
}
~B3()
{
cout << "call ~B3" << endl;
}
};
class V2 : public B1, public B2
{
public:
V2()
{
cout << "call V2" << endl;
}
~V2()
{
cout << "call ~V2" << endl;
}
};
class D2 : virtual public V2 ,public B3
{
public:
D2()
{
cout << "call D2" << endl;
}
~D2()
{
cout << "call ~D2" << endl;
}
};
class M1
{
public:
M1()
{
cout << "call M1" << endl;
}
~M1()
{
cout << "call ~M1" << endl;
}
};
class M2
{
public:
M2()
{
cout << "call M2" << endl;
}
~M2()
{
cout << "call ~M2" << endl;
}
};
class X : public D1,public D2
{
public:
X()
{
cout << "call X" << endl;
}
~X()
{
cout << "call ~X" << endl;
}
M1 m1_;
M2 m2_;
};
void main()
{
X b;
}
输出:
call B1
call V1
call B1
call B2
call V2
call D1
call B3
call D2
call M1
call M2
call X
析构函数于此相反。
X对象各子对象的构造顺序如下:
1.首先:构造虚基子类对象:
构造V1:B1::B1()V1::V1()
构造V2:B1::B1() B2::B2() V2::V2()
2.其次,构造非虚基类子对象:
构造 D1:D1::D1()
构造 D2:B3::B3() D2::D2()
3.再次,构造所有成员:
M1::M1()
M2::M2()
4. 构造X本身:
X::X()
分享到:
相关推荐
1.构造函数 2.继承 3.派生类初始化顺序
含有虚基类的派生类的构造函数有什么要求,什么是最远派生类,建立一个含有虚基类的派生类的对象时,为什么由最远派生类的构造函数负责虚基类的初始化?继承与组合之间的区别与联系是什么?派生类的构造函数是怎样的...
在 ClassFactory 类中,使用了一个静态的 map 成员变量来保存注册的类和对应的创建函数,get_map() 函数用来获取这个 map 的引用,避免了初始化顺序的问题。 工厂模式可以有效地解耦客户端代码和对象创建过程,有助...
但仅仅用建立对象的最远派生类的构造函数调用虚基类的构造函数,而该派生类的所有基类中列出的对虚基类的构造函数的调用在执行中被忽略,从而保证对虚基类子对象只初始化一次。 (7) 在一个成员初始化列表中同时出现...
如果有多个基类,则构造函数的调用顺序是某类在类派生表中出现的顺序,而不是它们在成员初始化表中的顺序。 2.成员类对象构造函数。如果有多个成员类对象则构造函数的调用顺序是对象在类中被声明的顺序,而不是...
7-2 答:(1)调用基类构造函数,调用顺序按照它们被继承时声明的顺序(从左到右);(2)对派生类新增的成员对象初始化,调用顺序按照它们在类中被声明的顺序;7-
3. 派生类构造函数的参数个数,必须满足多个基类初始化的需要。 4. 在多重继承下,当建立派生类对象时,系统首先调用各个基类的构造函数,调用顺序与定义派生类时指定的基类顺序一致。 多重继承范例: #include /*...
3.2.1 string对象的定义和初始化 70 3.2.2 String对象的读写 71 3.2.3 string对象的操作 72 3.2.4 string对象中字符的处理 76 3.3 标准库vector类型 78 3.3.1 vector对象的定义和初始化 79 3.3.2 vector对象的操作 ...
如果类派生自虚拟基类,则会将对象的虚拟基指针初始化。 如果类具有或继承了虚函数,则会将对象的虚函数指针初始化。虚函数指针指向类中的虚函数表,确保虚函数正确地调用绑定代码。 它执行自己函数体中的所有代码。
3.2.1 定义和初始化string对象 76 3.2.2 string对象上的操作 77 3.2.3 处理string对象中的字符 81 3.3 标准库类型vector 86 3.3.1 定义和初始化vector对象 87 3.3.2 向vector对象中添加元素 90 3.3.3 ...
3.2.1 定义和初始化string对象 76 3.2.2 string对象上的操作 77 3.2.3 处理string对象中的字符 81 3.3 标准库类型vector 86 3.3.1 定义和初始化vector对象 87 3.3.2 向vector对象中添加元素 90 3.3.3 ...
复习资料 1.1选择题 1.在一个C++程序中,main函数的位置( c )。 (a) 必须在程序的开头 (b) 必须在程序的后面 ( c ) 可以在程序的任何地方 (d) 必须在其它函数中间 2.... (a) 解释 (b) 汇编 (c) 编辑 (d) 编译 ...
(4)根据人类,派生一个学生类(Student),增加属性:学校(school)、学号(number)、平均成绩、语数外各科成绩(scores,一个数组),为该数组实现索引器, (5)定义Student的带参构造函数,实现学生属性的初始化,...
7.1.2 结构体类型变量的定义方法及其初始化 7.1.3 结构体变量的引用 7.1.4 结构体数组 7.1.5 指向结构体变量的指针 7.1.6 结构体类型数据作为函数参数 *7.1.7 动态分配和撤销内存的运算符new和delete 7.2 共用体 ...
7.1.2 结构体类型变量的定义方法及其初始化 7.1.3 结构体变量的引用 7.1.4 结构体数组 7.1.5 指向结构体变量的指针 7.1.6 结构体类型数据作为函数参数 *7.1.7 动态分配和撤销内存的运算符new和delete 7.2 共用体 ...
9.9 在派生类中使用构造函数和析构函数 9.10 将派生类对象隐式转换为基类对象 9.11 关于继承的软件工程 9.12 复合与继承的比较 9.13 对象的“使用”关系和“知道”关系 9.14 实例研究:类Point、CircIe和...
7.4.4 在构造函数中使用初始化列表 7.5 类的私有成员 7.5.1 访问私有类成员 7.5.2 类的友元函数 7.5.3 默认复制构造函数 7.6 this指针 7.7 类的const对象 7.7.1 类的const成员函数 7.7.2 类外部的成员函数定义 7.8 ...
7.4.4 在构造函数中使用初始化列表 7.5 类的私有成员 7.5.1 访问私有类成员 7.5.2 类的友元函数 7.5.3 默认复制构造函数 7.6 this指针 7.7 类的const对象 7.7.1 类的const成员函数 7.7.2 类外部的成员函数定义 7.8 ...
继承什么是继承为什么要继承如何用继承单继承多继承新式类、经典类继承与抽象派生类组合属性查找顺序重写子类中访问父类的内容子类初始化基类的私有成员类的mro方法菱形继承多态什么是多态为什么要用多态 ...