effective C++笔记之条款39: 避免“向下转换”继承层次

原创 2012年03月27日 16:15:00

  • 先看如下例子:

class Person {…};
class BankAccount
{
public:
         BankAccount(const Person *primaryOwner, const Person *jointOwner);
         virtual ~BankAccount();
         virtual void makeDeposit(double amount)= 0;
         virtual void makeWithdrawal(doubleamount) = 0;
         virtual double balance() const = 0;
         …
};
class SavingsAccount : public BankAccount
{
public:
        SavingsAccount(constPerson *primaryOwner, const Person *jointOwner);
         ~SavingsAccount();
         void creditInterest();   //给账户增加利息
                   …
 };

 假设为所有账户维持一个列表,通过list类模板实现。

         list<BankAccount*>allAccount;   //银行中所有账户

         现在准备写一段代码来遍历所有账户,为每个账户计算利息。如下所示代码:

         for(list<BankAccount*>::iterator p = allAccount.begin(); p != allAccounts.end();++p)

                  (*p)->creditInterest();  //错误

         因为creditInterest只是为SavingsAccount对象声明的,而不是BankAccount。

        

  • 向下转换:从一个基类指针到一个派生类指针。向下转换了继承的层次结构。
  •  通过向下转换可以得到通过编译,并正常运行。(static_cast<SavingsAccount *>(*p)->creditInterest();)但是对以后的扩充类难以维护。向下转换难看、容易导致错误,而且使得代码难于理解、升级和维护。
  •  向下转换可以通过如下两种方法消除:
  1.  最好的方法是将这种转换用虚函数调用来代替,同时,它可能对有些类不适用,所以要使这些类的每个虚函数成为一个空操作
  2. 加强类型约束,使得指针的声明类型和你所知道的真的指针类型之间没有出入。
  • 当不得不进行向下转换时,可以采用比原始转换更好的办法。这种方法称为“安全的向下转换”,通过dynamic_cast运算符来实现。当对一个指针使用dynamic_cast时,先尝试转换,如果成功(即指针的动态类型和正被转换的类型一致),就返回新类型的合法指针;如果dynamic_cast失败,返回空指针。

条款 39: 避免"向下转换" 继承层次

class Person { ... }; class BankAccount { public: BankAccount(const Person *primaryOwner, const Pers...
  • lujiandong1
  • lujiandong1
  • 2015年01月02日 20:46
  • 409

effective c++ 条款39: 避免 "向下转换" 继承层次

条款39: 避免 "向下转换" 继承层次  条款39: 避免 "向下转换" 继承层次 在当今喧嚣的经济时代,关注一下我们的金融机构是个不错的主意。所以,看看下面这个有关银行帐户的协议类(Prot...
  • fengxinziyang
  • fengxinziyang
  • 2010年09月27日 09:23
  • 427

《Effective C++》:条款38-条款39

条款38通过复合塑模树has-a 或根据某物实现出 条款39明智而审慎的使用private继承...
  • KangRoger
  • KangRoger
  • 2015年03月08日 21:32
  • 1163

《Effective C++》:条款28-条款29

条款28避免返回handles指向对象内部成分:指的是不能返回对象内部数据/函数的引用、指针等。 条款29为异常安全而努力是值得的:指的是要有异常处理机制,避免发生异常时造成资源泄露等问题。...
  • KangRoger
  • KangRoger
  • 2015年02月19日 19:47
  • 1399

Effective C++ 条款2

尽量以const、enum、inline替换#define首先,大家要明白一个道理。#define是什么,有什么作用。很简单,大家都知道#define实现宏定义,如下代码:#define Flag 1...
  • u011058765
  • u011058765
  • 2015年06月19日 12:06
  • 502

《Effective C++》:条款41-条款42

条款41了解隐式接口和编译期多态 条款42了解typename的双重意义条款
  • KangRoger
  • KangRoger
  • 2015年03月10日 22:13
  • 1250

避免 "向下转换" 继承层次

  • steven216
  • steven216
  • 2007年02月16日 11:21
  • 430

《Effective C++》:条款44-条款45

条款44将与参数无关的代码抽离templates 条款45运用成员函数模板接受所有兼容类型...
  • KangRoger
  • KangRoger
  • 2015年03月12日 22:01
  • 1513

Effective Modern C++ 条款23 理解std::move和std::forward

Effective Modern C++ 条款23
  • big_yellow_duck
  • big_yellow_duck
  • 2016年08月30日 17:11
  • 1243

《Effective C++》资源管理:条款13-条款15

在系统中,资源是有限的,一旦用完必须归还给系统,否则可能会造成资源耗尽或其他问题。例如,动态分配的内存如果用完不释放会造成内存泄漏。 这里说的资源不仅仅是指内存,还包括其他,例如文件描述符、网络连接、...
  • KangRoger
  • KangRoger
  • 2015年01月14日 21:46
  • 1336
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:effective C++笔记之条款39: 避免“向下转换”继承层次
举报原因:
原因补充:

(最多只允许输入30个字)