设为首页 加入收藏

TOP

9.6.6 间接基类
2013-10-07 12:38:50 来源: 作者: 【 】 浏览:56
Tags:9.6.6 间接

9.6.6  间接基类

本章一开始就说过,子类的基类可能是从另一个基类派生出来的。我们对上一个示例稍加扩充,就能提供这句话的例证,并示范跨越第二级继承的虚函数的用法。

试一试:多层继承

我们只需要在上一个示例得到的几个类中再添加一个CGlassBox类。现在拥有的几个类之间的关系如图9-6所示。

 
(点击查看大图)图  9-6

完全像以前那样,CGlassBox类是从CBox类派生出来的,但为了表明基类的函数版本还能通过派生类传播,我们故意省略了ShowVolume()函数的派生类版本。在上面显示的类层次结构中,CContainer类是CGlassBox类的间接基类,是CBox和CCan类的直接基类。

该示例的GlassBox.h头文件包含以下代码:

  1. // GlassBox.h for Ex9_11  
  2. #pragma once  
  3. #include "Box.h" // For CBox  
  4.  
  5. class CGlassBox: public CBox // Derived class  
  6. {  
  7. public:  
  8.  
  9. // Function to calculate volume of a CGlassBox  
  10. // allowing 15% for packing  
  11. virtual double Volume() const  
  12. { return 0.85*m_Length*m_Width*m_Height; }  
  13.    
  14. // Constructor  
  15. CGlassBox(double lv, double wv, double hv): CBox(lv, wv, hv){}  
  16. }; 

Container.h、Can.h和Box.h头文件包含的代码与Ex9_10示例中的相同。

下面是本示例中的源文件,其中的main()函数为使用层次结构中新添加的类而作了更新:

  1. // Ex9_11.cpp  
  2. // Using an abstract class with multiple levels of inheritance  
  3. #include "Box.h" // For CBox and CContainer  
  4. #include "Can.h" // For CCan (and CContainer)  
  5. #include "GlassBox.h" // For CGlassBox (and CBox and CContainer)  
  6. #include <iostream> // For stream I/O  
  7. using std::cout;  
  8. using std::endl;  
  9.  
  10. const double PI = 3.14159265; // Global definition for PI  
  11.  
  12. int main()  
  13. {  
  14. // Pointer to abstract base class initialized with CBox object address  
  15. CContainer* pC1 = new CBox(2.0, 3.0, 4.0);  
  16.  
  17. CCan myCan(6.5, 3.0); // Define CCan object  
  18. CGlassBox myGlassBox(2.0, 3.0, 4.0); // Define CGlassBox object  
  19.  
  20. pC1->ShowVolume(); // Output the volume of CBox  
  21. delete pC1; // Now clean up the free store  
  22.  
  23. // initialized with address of CCan object  
  24. pC1 = &myCan; // Put myCan address in pointer  
  25. pC1->ShowVolume(); // Output the volume of CCan  
  26.  
  27. pC1 = &myGlassBox; // Put myGlassBox address in pointer  
  28. pC1->ShowVolume(); // Output the volume of CGlassBox  
  29. cout << endl;  
  30. return 0;  

示例说明

如图9-6所示的类层次结构共有3层,其中CContainer是抽象的基类,因为它包含纯虚函数Volume()。main()函数现在使用指向基类的同一个指针,调用了ShowVolume()函数3次,但每次使该指针包含不同类的对象地址。因为这里的任何派生类都没有定义ShowVolume()函数,所以每个实例中调用的都是基类版本。基类CContainer的独立分支定义了派生类CCan。

该示例产生下面的输出:

  1. CBox usable volume is 24  
  2. Volume is 45.9458  
  3. CBox usable volume is 20.4 

输出显示,程序的执行根据每次所涉及对象的类型,从3个不同的Volume()函数中选择了正确的版本。

注意:

在赋予指针另一个地址值之前,我们必须从自由存储器中删除CBox对象。如果不这样做,以后我们将无法清理自由存储器,因为已经失去了原来对象的地址。当重新给指针赋值以及使用自由存储器时,这是个易犯的错误。

】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
分享到: 
上一篇9.6.4 纯虚函数 下一篇9.5.1 友元类

评论

帐  号: 密码: (新用户注册)
验 证 码:
表  情:
内  容: