Chinaunix首页 | 论坛 | 博客
  • 博客访问: 354717
  • 博文数量: 79
  • 博客积分: 1270
  • 博客等级: 中尉
  • 技术积分: 1370
  • 用 户 组: 普通用户
  • 注册时间: 2011-04-12 08:48
个人简介

freedom~~~~~~~~~~

文章分类

全部博文(79)

文章存档

2014年(10)

2013年(2)

2012年(13)

2011年(54)

分类: C/C++

2011-11-27 22:28:47

  1. #include<stdio.h>

  2. class left
  3. {
  4. public:
  5.     int show()
  6.     {
  7.         printf("this is left\n");
  8.     }
  9.     int lll()
  10.     {
  11.         printf("this is left llllllll\n");
  12.     }
  13. };

  14. class right
  15. {
  16. public:
  17.     int show()
  18.     {
  19.         printf("this is right\n");
  20.     }
  21. };

  22. class child:public left,public right
  23. {
  24. public:
  25.     int show()
  26.     {
  27.         left::show();
  28.         printf("this is child\n");
  29.     }
  30. };

  31. int main()
  32. {
  33.     child c;
  34.     c.show();
  35.     c.left::show();
  36.     c.right::show();
  37.     c.lll();
  38.     c.left::lll();
  39. }









  1. #include <stdio.h>

  2. class base
  3. {
  4.     public:
  5.         base()
  6.         {
  7.             printf("base con\n");    
  8.         }
  9.         void show()
  10.         {
  11.             printf("base show!!\n");
  12.         }
  13. };

  14. class left:public base
  15. {
  16. public:
  17.     left()
  18.     {
  19.             printf("left con\n");    
  20.     }
  21. };
  22. class right:public base
  23. {
  24.     public:
  25.         right()
  26.         {
  27.             printf("right con\n");    
  28.         }
  29. };

  30. class child_1:public left,public right
  31. {
  32. };

  33. class vleft:virtual public base
  34. {
  35.     public:
  36.         vleft()
  37.         {
  38.             printf("vleft con\n");    
  39.         }
  40.         void show()
  41.         {
  42.             printf("this is vleft show\n");
  43.         }
  44. };

  45. class vright:virtual public base
  46. {
  47.     public:
  48.         vright()
  49.         {
  50.             printf("vright con\n");    
  51.         }
  52. };

  53. class child_2:public vleft,public vright
  54. {
  55. };



  56. int main()
  57. {
  58.     child_1 c1;
  59.     child_2 c2;
  60.     //c1.show();
  61.     c2.show();
  62.     c2.vright::show();
  63. }
下面是摘抄的一段话:
  1. 1.被虚继承的类就是虚基类
  2. 2.何为虚继承: 先说普通继承
  3. 普通继承: class B: public A,
  4. B从A继承,B会将A做一份copy,作为自身的一部分,然后在加自己独有的一部分。
  5. 加入A是一个有虚函数的类,考虑A和B的结构
  6. sizeof(A) = sizeof(A的数据成员) + sizeof(vptr),这个vptr指向A类的 vtable
  7. sizeof(B) = sizof(A的数据成员) + sizeof(B数据成员) + sizeof(vptr),这个vptr指向B类的vtable

  8. 虚继承: 虚继承与普通继承不同点在于,子类不实际的copy父类的一部分,而是生成一个引用,指向父类对象
  9. 但是在用sizeof统计大小时,依然将父类的成员变量统计在内,此时B的结构如下:
  10. sizeof(B) = sizof(A的数据成员) + sizeof(B数据成员) + sizeof(vptr) + sizeof(pointer to A), vptr指向B类的vtable, 并且多了一个引用指向A对象

  11. 虚继承的这个特性在C++的多重继承应用中可以起到很好的作用:
  12. 一个没有虚继承的多重继承:
  13. class A
  14. {
  15.  void f() ;
  16. };
  17. class B: public A
  18. {
  19. };
  20. class C:public A
  21. {
  22. }
  23. class D: public B, public C
  24. {
  25. }
  26. void main()
  27. {
  28.  D d;
  29. d.f();
  30. }
  31. 这种情况下编译器会报错:D::f is ambiguous,could be the 'f' in base 'A' of base 'B' of class 'D',or the 'f' in base 'A' of base 'C' of class 'D'
  32. 很明显看出:d.f()是有歧义的,因为D中有2个A的copy,也就有2个A::f()函数,编译器不知道应该调用哪一个。

  33. 这个问题应用虚继承可以得到很好的解决,类定义重写如下:
  34. class A
  35. {
  36.  void f() ;
  37. };
  38. class B: public virtual A
  39. {
  40. };
  41. class C:public virtual A
  42. {
  43. }
  44. class D: public B, public C
  45. {
  46. }
  47. void main()
  48. {
  49.  D d;
  50. d.f();
  51. }
  52. 此时D中只指向一个A对象,调用d.f(),就是调用那个唯一的A的f()函数,没有歧义,顺利执行。因为此时B和C都是指向同一个A对象。
  53. 此时D的结构如下图:

  54. 需要注意的是B和C都必须是从A虚继承,只有一个是虚继承仍然会有歧义



阅读(948) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~