编译多态和运行多态

虚函数:(类的成员变量是虚函数)  //
1 :编译多态的时候就确定了。函数长的都一样,参数不一样。在声明,定义的时候确定
2 运行多态:
是指针的话,指针可以改变指向,在编译的时候不能确定是父类对象,or 子类对象。
只有在运行的时候才能确定。
如果是父类指针既可以指向父类,也可以指向子类。

1  :通常的做法是,这样所有的子类都不用定义指向自己的指针,同时继承一个父类指针。继承一套struct。
所有的子类用父类的指针指向自己即可。
如:
struct CascadeHdlrEntry
{
  CascadeHdlrTypeT type;
  const char  *pName;
  CascadeBase *pHdlr;
};
//hdlrType是各种子类,如ResourceMgr,TaMgr,FileMgr etc
hdlrType = getMotherSignalHdlr(sigP->sigNo);
cascadeHdlrs[hdlrType].pHdlr->signalHandler(sigP);
如果没有case1的功能,则pHdlr需要根据hdlrType定义pHdlr1,pHdlr2,pHdlr3,etc 
定义不同的子类指针指向不同的子类。但是有case1功能。这样就不用定义数组,所有的子类用一个struct。用一个基类指针。
如果采用pHdr1,2,3是c的变成风格。c也能实现这个多态功能.
用基类重载,run的时候根据赋值,确定是哪个子类,是resoucemgr,or tamgr or base etc。
具体见反例论证

(QA:父类指针肯定可以指向子类。子类指针可以指向父类吗?

用派生类指针引用基类的对象。这种引用方式会导致语法错误。派生类指针必须先强制转换为基类指针,这种方法是不安全的。

http://blog.sina.com.cn/s/blog_3ce156ce01000af4.html


2: 虚函数指针: signalHandler是用的父类 or 子类的signHandler,当根据hdlrType知道了是哪个子类。子类根据虚函数表,确定用自己重写的函数。

具体见虚函数表.详见陈皓对虚函数表的论述。
cascadeHdlrs[hdlrType].pHdlr->signalHandler(sigP);


3: CascadeBase *pHdlr; 
cascadeHdlrs[hdlrType].pHdlr->signalHandler(sigP);
不要看指针的定义,要看指针的指向。是父类or子类. 父类的指针只能指向父类定义,并且子类重载的函数。
如果是子类定义的函数,父类指针不能调用.
比如:
http://bbs.csdn.net/topics/390853050 中
//pb->Out();    //无法被调用


notes: 中间删掉了自己对数组赋值是run的比较,删掉了3和cscade signal的比较。同时子类不能指向父类和父类不能调用子类non-virtual没有不计较,因为一个是类,一个函数level,没有可比性

===================================
http://bbs.csdn.net/topics/390853050

虚函数表:关于子类重写virtual,则子类的函数放在第一个(本来是最后的变成第一个)是看什么书,得出的结论呢?

 从blog上看是从vc的编译器看内存得出的结论。


==================================

反例论证:

1 是数组init不能 : cascadephlr[]={new(), resourcemgr.getinstance(),...};  // 既不能new,也不能getinstance。还是run状态

cascade[].phlr={...}; //这是一个指针,不是数组。run状态的数组,是loop。是n句执行命令。
2 第一个例子: 既可以指父类又指子类
  cascadeHdlrs[CASCADE_NONE_HDLR].pHdlr         = new CascadeBase;
  cascadeHdlrs[CASCADE_FILE_HDLR].pHdlr         = CascadeFileMgr::getInstance();
    cascadeHdlrs[CASCADE_RESOURCE_HDLR].pHdlr     = CscdResourceMgr::getInstance();
第二个例子: 
  run唯一。  不是唯一。
  例子,实现了。
   p1= cascaderm.getinstance();
   p2=cascadeta.getinstance();
    cascadeHdlrs[CASCADE_FILE_HDLR].pHdlr = p1 (p1 只需要是一个地址即可,如rm )
    然后可以换成    cascadeHdlrs[CASCADE_FILE_HDLR].pHdlr = p2 (另一个地址即可,如ta)
    和所有的指针用法一样。可以更换指向。
    不是唯一性,仅仅是本项目不可以。
      pHdlr= new Derive(); 会造成内存泄漏.可以不指向new的东西,指向new的东西更改方向会造成泄漏。指向指针变量则会随便更改。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值