zoukankan      html  css  js  c++  java
  • 虚基类

    解决多重继承中,一个公共基类可能在派生类中产生多个拷贝的现象。

    如:有一个公共基类A,类B和类C都有类A派生,类D由类B和类C派生,则类D含有类A的两个拷贝,这不仅多占内存,还可能造成多个拷贝中的数据不一致。

    #include <iostream>
    using namespace std;
    class A {
    public:
    	int x;
    	A(int a = 0) { x = a; }
    };
    
    class B:public A {
    public:
    	int y;
    	B(int a = 0, int b = 0):A(b) { y = a; }
    	void PB() { cout << "x=" << x << "y=" << y << '\n'; }
    };
    
    class C:public A {
    public:
    	int z;
    	C(int a = 0, int b = 0):A(b) { z = a; }
    	void PC() { cout << "x=" << x << "z=" << z << '\n'; }
    };
    
    class D:public B, public C {
    public:
    	int m;
    	D(int a, int b, int d, int e, int f):B(a, b), C(d, e) { m = f; }
    	void Print() {
    		PB();
    		PC();
    		cout << "m=" << m << '\n';
    	}
    };
    
    int main(void)
    {
    	D d(100, 200, 300, 400, 500);
    	d.Print();
    	return 0;
    }
    
    
    输出:

    x=200y=100
    x=400z=300
    m=500

     

    D中包含类A的两个拷贝,从两个不同的x可以看出来。

     

     

     

    在多重接继承中,如果希望公共基类在派生类中只有一个拷贝,可在定义派生类时将公共基类的类名前加上virtual即可。

    #include <iostream>
    using namespace std;
    class A {
    public:
    	int x;
    	A(int a = 0) { x = a; }
    };
    
    class B:virtual public A { //加virtual
    public:
    	int y;
    	B(int a = 0, int b = 0):A(b) { y = a; }
    	void PB() { cout << "x=" << x << "y=" << y << '\n'; }
    };
    
    class C:virtual public A { //加virtual
    public:
    	int z;
    	C(int a = 0, int b = 0):A(b) { z = a; }
    	void PC() { cout << "x=" << x << "z=" << z << '\n'; }
    };
    
    class D:public B, public C {
    public:
    	int m;
    	D(int a, int b, int d, int e, int f):B(a, b), C(d, e) { m = f; }
    	void Print() {
    		PB();
    		PC();
    		cout << "m=" << m << '\n';
    	}
    };
    
    int main(void)
    {
    	D d(100, 200, 300, 400, 500);
    	d.Print();
    	return 0;
    }
    
    
    输出:

    x=0y=100
    x=0z=300
    m=500

     

    解释:先调用虚基类的构造函数,然后调用非虚基类的构造函数。

     

    类D的构造函数分别调用类B和类C的构造函数,由于类A在类D中只有一个拷贝,编译器无法确定是由类B还是类C的构造函数来调用类A的构造函数,这种情况下,编译器约定执行类B和类C的构造函数时都不调用虚基类A的构造函数,二是子类D的构造函数中直接调用虚基类A的默认构造函数,因此x为0.

  • 相关阅读:
    为什么RedLock并不能100%解决Redis做分布式锁的问题?
    阿里巴巴sentinel熔断降级(请求方是浏览器、请求方是应用两种方式考虑)
    阿里巴巴sentinel里面熔断里面RT是什么意思?(是什么单词的缩写)
    人生而孤独,却渴望陪伴。
    教你从官网下载commons-logging jar包(授人鱼不如授人以渔)
    spring5学习笔记-demo1
    企业网络规划
    scapy 查找自己的网卡(默认网卡)
    前端开发中常用的几种设计模式
    webpack打包原理
  • 原文地址:https://www.cnblogs.com/helloweworld/p/2840992.html
Copyright © 2011-2022 走看看