首 页 | 新 闻 | Symbian | Android| Windows Mobile | J2ME | 下载中心 | 游戏策划招聘与求职 | 购书指南 | 视频教程
您现在的位置: 开发视界 >> Symbian >> 语言基础 >> 正文
关于成员指针
作者:小兵    文章来源:小兵    更新时间:2006-12-18 15:46:11
★ 关于函数成员指针

1. 派生类的成员指针可以指向基类的相应成员;
2. 基类的成员指针不一定可以指向派生类的相应成员;
   1) 如果派生类覆写了基类的函数,不可以;
   2) 如果派生类没有覆写基类的函数,可以;
   3) 如果是派生类中新加的函数,不可以。

原因:
1. 派生类具有基类的所有成员
2. 1) 此时基类和派生类中的该函数声明一样,定义不一样;如果此时允许基类该函数的指针指向派生类的该函数,则在用基类指针调用该指针指向的函数时,调用的将是基类中的该函数,这就违背了用户的本义;因此不可以;
   2) 此时基类和派生类中的该函数从声明到定义都一模一样;
   3) 派生类中的该成员在基类中不存在

例子程序:
############### 不包括本行 ##############
/******************************************
 * 文件名:testMemberPointer.cpp
 * 描述:测试成员指针
 * 结论:1. 派生类的成员指针可以指向基类的相应成员;
 *       2. 基类的成员指针不一定可以指向派生类的相应成员;
 *          1) 如果派生类覆写了基类的函数,不可以;
 *          2) 如果派生类没有覆写基类的函数,可以;
 *          3) 如果是派生类中新加的函数,不可以。
 * 作者:Lin Xiaobin
 * 创建时间:2006-11-04
 ********************************************/

#include <iostream>

using std::cout;
using std::endl;

class Base
{
public:
    virtual void func()
    {
        cout << "base.func" << endl;
    }

    void f()
    {
        cout << "another base.func" << endl;
    }
};

class Derived : public Base
{
public:
    void func()
    {
        cout << "derived.func" << endl;
    }
};

int main(int argc, char *argv[])
{
    typedef void (Base::*PBMF)();
    typedef void (Derived::*PDMF)();
    typedef int Base::*PBMD;    // 允许,虽然 Base 类里没有 int 数据成员
    typedef int Derived::*PDMD; // 允许,虽然 Derived 类里也没有 int 数据成员

    PBMD p;     // 允许,虽然 Base 类里没有 int 数据成员

    Base *bd = new Derived; // 可以
    Base *b = new Base;     // 可以
    //Derived *db = new Base; // 错误,无法将类型 Derived* 转换为类型 Base*。
    Derived *d = new Derived;

    //PBMF pbmf1 = &Derived::func;    // 错误,派生类覆写了函数 func,
                                    // 无法将类型 void(Derived::*)()
                                    // 转换为类型 void(Base::*)()。
    PBMF pbmf2 = &Base::func;       // 可以
    PBMF pbmf3 = &Base::f;          // 可以
    PBMF pbmf4 = &Derived::f;       // 可以,派生类没有覆写函数 f

    PDMF pdmf1 = &Derived::func;    // 可以
    PDMF pdmf2 = &Base::func;       // 也可以

    (d->*pbmf2)();  // 可以,若为虚函数,调用 Derived::func,否则调用 Base:func
    (d->*pdmf1)();  // 可以,调用 Derived::func
    (d->*pdmf2)();  // 可以,若为虚函数,调用 Derived::func,否则调用 Base:func

    (b->*pbmf2)();  // 可以,调用 Base::func
    //(b->*pdmf1)();  // 错误,类型不兼容
    //(b->*pdmf2)();  // 错误,类型不兼容

    (bd->*pbmf2)(); // 可以,若为虚函数,调用 Derived::func,否则调用 Base:func
    //(bd->*pdmf1)(); // 错误,类型不兼容
    //(bd->*pdmf2)(); // 错误,类型不兼容

    return 0;
}
############### 不包括本行 ################

★ 关于数据成员指针
参考:http://www.zdnet.com.cn/developer/code/story/0,3800066897,39308240,00.htm
相关文章:
遍历文件夹
如何在进程间共享文件句柄
MMI of UIQ (三)
Symbian系统中DLL的冻结
如何改变CEikLabel的颜色
创建Log文件调试Symbian程序
CCoeControl类中Draw()函数的调试
Symbian程序中的观察者模式
 

站点地图 | 加入收藏 | 联系站长 | 广告服务 |
QQ:280529124  Tel:0592-8271361 辽ICP备05021703号