首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

虚拟继承和静态继承 - 在C++中混合

虚拟继承和静态继承是C++中的两种不同的继承方式,它们都是为了解决继承中的一些问题而产生的。

虚拟继承是指在多重继承中,派生类可以通过虚基类来继承基类的成员,从而避免了在派生类中出现多个基类的同名成员。虚拟继承可以通过虚继承关键字来实现,即在派生类中使用虚继承关键字来声明基类,这样就可以在派生类中共享基类的成员,而不会出现重复的成员。

静态继承是指在多重继承中,派生类可以通过静态成员来继承基类的成员,从而避免了在派生类中出现多个基类的同名成员。静态继承可以通过在派生类中声明基类的静态成员来实现,这样就可以在派生类中共享基类的成员,而不会出现重复的成员。

总的来说,虚拟继承和静态继承都是为了解决继承中的一些问题而产生的,它们都可以在派生类中共享基类的成员,而不会出现重复的成员。但是,它们的实现方式不同,虚拟继承使用虚继承关键字来实现,而静态继承使用静态成员来实现。

页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

C++继承(定义、菱形继承虚拟继承

继承,一般用公有保护,少用私有。 总结: 基类private成员派生类无论以什么方式继承都是不可见的。...切片有赋值兼容,赋值的时候不会产生临时对象,就不需要加const。如下图,此时ref是直接指向派生类基类的那一部分。 继承的作用域 继承体系基类派生类都有独立的作用域。...B的funA的fun不是构成重载,因为不是同一作用域 。 B的funA的fun构成隐藏,成员函数满足函数名相同就构成隐藏。 想在子类对象调用父类方法也要加上类域。...继承与友元 友元关系不能继承,也就是说基类友元不能访问子类私有保护成员 。 继承静态成员 基类定义了static静态成员,则整个继承体系里面只有一个这样的成员。...如上面的继承关系,Student Teacher的继承Person时使用虚拟继承,即可解决问题。

1600

C++ 虚拟继承

1.为什么要引入虚拟继承 虚拟继承是多重继承特有的概念。虚拟基类是为解决多重继承而出现的。如:类D继承自类B1、B2,而类B1、B2都继 承自类A,因此类D两次出现类A的变量函数。...实现的代码如 下: class A class B1:public virtual A; class B2:public virtual A; class D:public B1,public B2; 虚拟继承一般的应用很少用到...,所以也往往被忽视,这也主要是因为C++,多重继承是不推荐的,也并不常用,而一旦离开了多重继承虚拟继承就完全失去了存在的必要因为这样只会降低效率占用更多的空间。...2.引入虚继承直接继承会有什么区别呢 由于有了间接性共享性两个特征,所以决定了虚继承体系下的对象访问时必然会在时间空间上与一般情况有较大不同。...虚拟继承与普通继承不同的是,虚拟继承可以防止出现diamond继承时,一个派生类同时出现了两个基类的子对象。也就是说,为了保证 这一点,虚拟继承情况下,基类子对象的布局是不同于普通继承的。

2.2K80

C++继承的多继承语法与菱形继承

继承语法 C++允许一个类继承多个类 语法: class 子类 :继承方式 父类1 , 继承方式 父类2......多继承可能会引发父类中有同名成员出现,需要加作用域区分 C++实际开发不建议用多继承 示例: class Base1 { public: Base1() { m_A = 100; } public...; cout << s.Base2::m_A << endl; } int main() { test01(); system("pause"); return 0; } 总结: 多继承如果父类中出现了同名情况...,子类使用时候要加作用域 菱形继承 菱形继承概念: ​ 两个派生类继承同一个基类 ​ 又有某个类同时继承者两个派生类 ​ 这种继承被称为菱形继承,或者钻石继承 典型的菱形继承案例: 菱形继承问题:...使用了虚继承后对比未使用虚继承解决菱形继承 总结: 菱形继承带来的主要问题是子类继承两份相同的数据,导致资源浪费以及毫无意义 利用虚继承可以解决菱形继承问题

69910

C++继承 ⑩ ( 继承机制的 static 静态成员 | 子类访问父类静态成员的方法 )

一、继承机制中派生类的 static 关键字 1、子类继承父类静态成员 子类继承父类静态成员 : 父类 ( 基类 ) 使用 static 关键字 定义的 静态成员变量 , 可以被所有的 子类 (...派生类 ) 共享 ; 2、父类静态成员访问控制权限的改变 继承自 父类的 静态成员变量 , 仍然遵循 继承 子类的 访问控制特性 , public 公有继承 : 父类成员 子类 , 访问控制权限...不变 , 共有 保护成员 可以子类访问 , 私有成员不可在子类访问 ; 父类的 public 成员 仍然是 public 成员 ; 父类的 protected 成员 仍然是 protected... 保护成员 可以子类访问 , 私有成员不可在子类访问 ; 父类的 public 成员 变为 子类的 protected 成员 ; 父类的 protected 成员 仍然是 protected...; 或 对象名.静态成员名 child.c = 30; 的方式 , 访问 继承自 父类的 静态成员 ; 4、静态成员使用要点 参考 【C++静态成员变量 ( 静态成员变量概念 | 静态成员变量声明 |

33410

c++C++继承&&菱形继承详解

继承体系基类派生类都有独立的作用域 子类父类中有同名成员,子类成员将屏蔽父类对同名成员的直接访问,这种情况叫隐藏,也叫重定义。...funA的fun不是构成重载,因为不是同一作用域 B的funA的fun构成隐藏,成员函数满足函数名相同就构成隐藏 // B的funA的fun不是构成重载,因为不是同一作用域 //...如上面的继承关系,StudentTeacher的继承Person时使用虚拟继承,即可解决问题。...通过偏移量可以找到下面的A 下面是上面的Person关系菱形虚拟继承的原理解释 8.继承的总结反思 很多人说C++语法复杂,其实多继承就是一个体现。...如何解决数据冗余二义性的 菱形继承问题继承是如何解决二义性与数据冗余的_数据的二义性-CSDN博客 C++继承的问题 : 菱形继承 (虚拟继承)_c++菱形继承问题-CSDN博客 3.

8210

静态成员PHP是怎么继承的?

静态成员PHP是怎么继承的? 静态成员,也就是用static修饰的变量或者方法,如果搞不清楚它们实现的原理,就很容易会出现一些错误。这次我们来研究的是继承静态成员的调用情况。...好了,有了这个基础之后,我们知道静态成员是类有关的,对象无关。那么以下的代码也就更容易理解了。...static $c = 1; public $d = 1; } class D extends C { public function add() { self::$c+...$c是静态变量,$d是普通变量。通过类实例的add()方法进行操作后,$c因为是类有关,所以不管是哪个实例对象,操作它之后都会是共享的。而$d作为普通变量,它的作用域仅限制在当前这个实例对象。...因此,输出的结果是: c:2,d:2; c:3,d:2; 最后,我们还是来复习一次self、parentstatic关键字。

1.4K20

继承、占位符混合

四、继承、占位符混合宏 很多初学者刚刚接触的时候,都容易纠结什么时候用混合宏,什么时候用继承,然后什么时候用占位符。其实,这3个都有它们自身的优缺点。...这一节我们来详细探讨一下这3个实际开发的不同。...继承、占位符混合宏的声明方式调用方式 方法 声明方式 调用方式 继承 .class @extend 占位符 %placeholder @extend 混合宏...@mixin @include 一、继承混合宏 对于继承(包括@extend%placeholder)混合宏,我们总结出以下几点: (1)继承混合宏都能实现相同代码块的重用,极大提高开发效率...实际开发的过程,对于“功能代码块”(类似于JavaScript的函数)我们都是使用混合宏来实现的,因为功能代码块往往是可以通过传递不同的参数来满足我们开发的不同需求。

83730

C++继承

,但是会存在越界访问的问题 //ps2->_No = 10; } 继承的作用域 继承体系基类派生类都有独立的作用域。...funA的fun不是构成重载,因为不是同一作用域 // B的funA的fun构成隐藏,成员函数满足函数名相同就构成隐藏。...无论派生出多少个子类,都只有一个static成员实例 静态成员一些地方有应用,例如: 要统计下面子类创建了多少个子类对象,就有以下这种办法 我们子类定义一个静态成员count(注意静态成员要在类外面初始化...如上面的继承关系,StudentTeacher的继承Person时使用虚拟继承,即可解决问题。需要注意的是,虚拟继承不要在其他地方去使用,只有菱形继承时使用。..._name = "peter"; } 虚拟继承的原理 其实这个原理的讲解很复杂,博主的知识讲解能力有限,所以只给出结论: 它在继承之后并不会创造出两个基类成员来给派生类继承,而是派生类记录两个偏移量

8110

C++继承 ⑦ ( 继承的对象模型分析 | 继承的构造函数析构函数 )

, 除了继承自 B 类的 int x int y 成员 , 还有一个自己的 int z 成员 , 在内存是 3 个 int 类型的空间 ; 3、问题引入 - 派生类对象构造函数析构函数调用...上述 继承 的过程 , 每一层继承 , 都继承了上一级 父类的 成员变量 , 同时自己也定义了新的成员变量 ; 派生类对象 构造时 , 构造函数如何进行调用 ; 派生类对象 析构时 , 析构函数如何进行调用...int main() { A objA; B objB; C objC; // 控制台暂停 , 按任意键继续向后执行 system("pause"); return 0; } 二、继承的构造函数析构函数...---- 1、子类构造函数与析构函数调用顺序 继承的构造函数析构函数 : 子类构造 : 子类对象 进行 构造 时 , 需要调用 父类 的 构造函数 对 继承自父类的 成员变量 进行 初始化 操作...public A { public: B(int a, int b) : A(a) { this->y = b; cout << "B 构造函数调用" << endl; } } 3、代码示例 - 继承的构造函数析构函数

19540

Python类的继承、多层继承继承

Python,一个类可以通过继承的方式来获得父类的非私有属性非私有方法。...一、继承、重写、调用重写的父类方法 继承的语法为类名后的小括号()写入要继承的父类名,如果要继承多个类则中间用逗号分隔。...当子类实现一个父类同名的方法时,叫做重写父类方法。直接在子类定义与父类同名的方法,然后方法实现子类的业务逻辑,子类方法就会覆盖父类的同名方法。...4.如果在子类重写父类的方法,需要使用父类同名方法的功能,父类功能基础上做扩展,则子类可以重写的方法调用父类被重写的方法,使用super()来调用。 ? 二、类的多层继承 类可以多层继承。...当Mi类对象调用属性方法时,优先在自己的内部查找是否有该属性方法,如果没有会到它的父类Phone查找该属性方法,如果没有会继续往上Phone的父类Electrical查找,一直查找到object

5.2K30

C++继承

③private继承:当子类通过private继承,那么父类的那么父类的private成员private成员子类中都是子类的private成员。...继承的作用域 ⭐1.继承体系基类派生类都有独立的作用域 ⭐2.派生类基类中有同名成员,派生类成员将屏蔽基类对同名成员的直接访问,这种情况叫隐藏,也叫重定义。...多继承本身没啥问题,但是多继承带来了一种特殊的继承方式:菱形继承。菱形继承会导致代码冗余二义性的问题,这是C++初次设计多继承时留下了的问题。...虚拟继承 虚拟继承可以解决菱形继承的二义性和数据冗余的问题。如上面的继承关系,StudentTeacher的继承Person时使用虚拟继承,即可解决问题。...需要注意的是,虚拟继承不要在其他地方去使用。如下面代码:Student类Teacher类继承Perosn的继承方式后加上关键字virtual。

94530

C++】复杂的菱形继承 及 菱形虚拟继承的底层原理

继承 在上一篇文章,我们给大家演示的其实都是单继承。 单继承的概念: 单继承:一个子类只有一个直接父类的继承关系为单继承 2. 多继承 然后呢C++里面还支持多继承,那什么是多继承呢?...3.1 菱形继承的问题——数据冗余二义性 菱形继承就会存在一个数据冗余二义性的问题 从下面的对象成员模型构造可以看出,Assistant的对象Person成员会有两份。...那为了更好的解决菱形继承导致的数据冗余二义性的问题,C++就引入了虚拟继承… 3.2 解决方法——虚拟继承 C++引入了虚拟继承可以解决菱形继承的二义性和数据冗余的问题 那虚拟继承是怎样的呢?...虚拟继承可以解决菱形继承的二义性和数据冗余的问题。 如上面的继承关系,StudentTeacher的继承Person时使用虚拟继承,即可解决问题。需要注意的是,虚拟继承不要在其他地方去使用。...继承的反思总结 很多人说C++语法复杂,其实多继承就是一个体现。有了多继承,就存在菱形继承,有了菱形继承就有菱形虚拟继承,底层实现就很复杂。所以一般不建议设计出多继承,一定不要设计出菱形继承

28110

C++继承多态

继承的作用域 继承体系父类子类都有独立的作用域。 父类子类中有同名成员,子类成员将屏蔽父类对同名成员的直接访问,这种情况叫隐藏,也叫重定义。...但是有一种方法可以既解决二义性,也解决数据冗余问题,就是虚拟继承虚拟继承可以解决菱形继承的二义性和数据冗余的问题。 如上面的继承关系, B C 继承 A 时使用虚拟继承,即可解决问题。...(2)虚拟继承解决数据冗余二义性的原理 首先我们先通过调试观察一下普通菱形继承,d 对象的内存分布,如下图所示: 我们可以观察到 d 对象中有两份 _a ,明显的数据冗余。...接下来我们加上虚拟继承,继续观察 d 对象的内存分布,如下图: 上图是菱形虚拟继承的内存对象成员模型:这里可以分析出 D 对象中将 A 放到的了对象组成的最下面,这个 A 同时属于 B C,那么...(3)动态绑定与静态绑定 静态绑定又称为前期绑定(早绑定),程序编译期间确定了程序的行为,也称为静态多态,比如:函数重载; 动态绑定又称后期绑定(晚绑定),是程序运行期间,根据具体拿到的类型确定程序的具体行为

13010

C++继承的对象模型与继承构造析构顺序

继承的对象模型 问题:从父类继承过来的成员,哪些属于子类对象?...Studio 的开发人员命令提示符 打开工具窗口后,定位到当前CPP文件的盘符 然后输入: cl /d1 reportSingleClassLayout查看的类名 所属文件名 效果如下图: 结论: 父类私有成员也是被子类继承下去了...,只是由编译器给隐藏后访问不到 继承构造析构顺序 子类继承父类后,当创建子类对象,也会调用父类的构造函数 问题:父类子类的构造析构顺序是谁先谁后?...<< endl; } }; void test01() { //继承 先调用父类构造函数,再调用子类构造函数,析构顺序与构造相反 Son s; } int main() { test01...(); system("pause"); return 0; } 速记:构造时现有父亲后又儿子,析构顺序相反(白发送黑发) 总结:继承 先调用父类构造函数,再调用子类构造函数,析构顺序与构造相反

56720

C++虚拟继承与虚基类

1.多重继承带来的问题 C++虚拟继承一般发生在多重继承的情况下。C++允许一个类有多个父类,这样就形成多重继承。...所以,在上面的程序show()显示的是Employee的成员(IDPersonName)。...实际上,EGStudent类对象还有来自Student类的成员(IDPersonName)。...虚拟继承就是解决这个问题的,通过把继承关系定义为虚拟继承构造EGStudent类对象的时候,EGStudent类的祖先类Person的对象只会被构造一次,这样就可以避免存在多个IDPersonName...因为虚拟继承只是表名某个基类的对象派生类对象只被构造一次,而在本例类StudentEmployee对象EGStudent对象本来就不会被构造多次,所以不将它们申明虚基类也是完全可以的。

86520

C++继承 ⑨ ( 继承成员变量同名的处理方案 )

一、继承成员变量同名的处理方案 1、继承成员变量同名的场景说明 子类 继承 父类 的 成员 , 如果 子类 定义了 与 父类成员变量 同名的 变量 , 子类 仍然 可以 继承 父类的 同名 成员变量...: 继承自父类的成员变量 , 使用 父类名称::成员变量名称 替代 成员变量名称 , 如 : Parent 是父类名称 variable 是父类的变量名称 如果子类也定义了 variable...Child : public Parent { public: int b, c; }; 显然 , 父类 Parent 子类 Child , 成员变量 b 发生了冲突 , 父类 子类 各自定义了一个成员变量..., 也可以不使用域作用符 , 直接访问 b ; 子类 Child , 定义了 print 成员函数 , 该函数 , 通过 Parent::b 访问 继承自父类的 b 成员 , 通过 Child:...类外部 , 通过 子类对象名.父类名::变量名 的方式 , 访问 继承自父类的 成员变量 ; Child child; // 访问 子类对象 child 继承自 父类的 b 成员 child.Parent

27120

C++进阶学习】第三弹——菱形继承虚拟继承——菱形继承的二义性和数据冗余问题

前言: 在前面,我们已经讲过继承的相关知识,今天我们来将一个由继承拓展出来的很重要的知识,那就是——菱形继承虚拟继承及相关知识讲解 一、单继承继承 C++继承 C++,单继承是指一个类只能继承自一个基类...菱形继承很容易带来冗余性二义性,这些就需要我们用虚拟继承来解决,这些问题挺重要,我们往下看 二、菱形继承 C++的菱形继承是指在类的继承关系,存在两个或更多个直接或间接的基类,它们之间形成了一个类似菱形的结构...下面我们来讲解一种解决上面问题的方法——虚拟继承 三、虚拟继承继承是一种特殊的继承方式,用于解决菱形继承的冗余性二义性问题。了解虚继承的相关知识点有助于更好地使用它。...虚基类:继承,被继承的类被称为虚基类。 虚基类的成员变量成员函数子类只会存在一份,避免了冗余性问题。...因此,虚继承应该谨慎使用,只必要时才使用。 总之,C++ 通过虚继承解决了菱形继承的冗余性二义性问题,使得使用继承时更加灵活安全。

6610

C++接口继承与实现继承的区别选择

1.接口继承与实现继承的区别 《Effective C++》条款三十四:区分接口继承实现继承中介绍的比较啰嗦,概括地说需要理解三点: (1)纯虚函数只提供接口继承,但可以被实现; (2)虚函数既提供接口继承...虚函数可以基类多个派生类中提供不同的版本,利用多态性质,程序运行时动态决定执行哪一个版本的虚函数(机制是编译器生成的虚表)。...virtual关键字基类必须显式指明,派生类不必指明,即使不写,也会被编译器认可为virtual函数,virtual函数存在的类可以定义实例对象。...基类CShape,不能够为每一种不同的图形提供一个默认的draw实现,所以设置为纯虚函数,留给派生类来实现,也就说派生类只是继承了一个借口而已。...---- 参考文献 [1]读书笔记Effective_C++条款三十四:区分接口继承实现继承 [2]李健.编写高质量代码:改善C++程序的150个建议[M].第一版.北京:机械工业出版社,2012.1

1.2K20

Python 子类调用父类方法详解(单继承、多层继承、多重继承

测试环境: win7 64位 Python版本:Python 3.3.5 代码实践: 1、子类通过“类名”调用父类的方法 class FatherA: def __init__(self)...__init__(self) # 子类调用父类的方法:父类名.方法名称(参数) if __name__ == '__main__': b = SubClassB() 运行结果: >>> ==...in father class A 缺点:当一个子类的父类发生变化时(如类SubClassB的父类由FatherA变为FatherD时),必须遍历整个类定义,把子类中所有的父类类名全部替换过来 2、子类通过...__init__() # 子类调用父类的方法:super().方法名称(参数) if __name__ == '__main__': b = SubClassB() class FatherA...,以super().method(参数)方法调用父类的方法,如果不同父类存在同名方法method(不管参数列表是否相同),则按继承顺序,选择第一个父类的方法。

2.9K30

详细对比php继承接口继承

frist 第二个类第三个类没有重写printer()方法,第三个类实例化后可以调用printer()方法。...,不能重新private的方法,如果同名只是本类重新声明 3、接口类继承 (1) 接口支持多继承,接口类的方法不需要实现比如: interface frist{ public function...(3)继承的派生类当中要把所有抽象方法重载才能实例化。 (4)抽象类实现的普通发放,可以非抽象子类中直接调用。...5、接口抽象类的异同点(引用抽象类与接口区别) (1)对接口的使用方式是通过关键字implements来实现的,而对于抽象类的操作是使用类继承的关键字exotends实现的 (2) 接口没有数据成员,...(4)接口中的方法都是public类型,而抽象类的方法可以使用private、protected或public来修饰。 (5) 一个类可以同时实现多个接口,但是只能实现一个抽象类。

1.1K20
领券