evilknight 发表于 2009-8-19 20:28:21

手工模拟了一下虚表

有問題的話直接在下面留言就好了!不要拍砖就行了!
/*
虚函数原理
手工模拟虚函数来表现出多态性:
写一基类Person
有sayHello,sayGoodbye函数
有一子类student
它也有自己的sayHello, sayGoodbye函数
请在这两个类里加入函数vsayHello, vsayGoodbye函数
来表现出对象的多态性(分别调用自己的对应的sayHello和sayGoodbye)

修改(8.21):修正了原来用指针不能正确调用的问题!
原来是每个类一张私有的,导致调用不正确,现在改成保护的,derived直接在基类的那
张表上面修改
*/

#include <iostream>
#include <string>
using namespace std ;
// 函數指針,不属于哪个类的
typedef void (*vft)(void) ;

class person
{
private:
    // person成员函数指针
    typedef void (person::*FUN)(void) ;
    FUN      fun ;// 用来保存二个成员函数的地址

    // public inte**ce
public:
    // 通过调用函数指针,执行sayHello,这样只是方便调用而已
    void SayHello(void)
    {
      // 调用sayHello 等价于 person::sayHello() ;
      _vft();
    }
    void SayGoodbye(void)
    {
      _vft() ;
    }
   
protected:
    // 传说中手工模拟出来的虚表
    vft      _vft ; // 用来保存二个函数的地址
   
private:
    // 摸拟这二个的多态,不是函数重载,函数名首字符不同的
    // 这里函数名随便起一个都行,只是下面指对了就行了
    void sayHello(void)
    {
      cout << "person sayHello " << endl ;
    }
   
    void sayGoodbye(void)
    {
      cout << "person sayGoodbye" << endl ;
    }
   
public:
    person();
    virtual ~person() ;
} ;

person::person(void)
{
    fun = &person::sayHello ;
    fun = &person::sayGoodbye ;
    // 将成员函数的地址复制到_vtf中去,直接复制省去了强制转换
    memcpy(_vft, fun, sizeof(int) * 2) ;
}

person::~person(void)
{
    fun = NULL ;
    fun = NULL ;
    _vft = NULL ;
    _vft = NULL ;
}

class student:public person
{
private:
    // 学生类成员函数指针
    typedef void (student::*FUN)(void) ;
    FUN      fun ;
   
public:
    void SayHello(void)
    {
      _vft();
    }
    void SayGoodbye(void)
    {
      _vft() ;
    }

private:
    void sayHello(void)
    {
      cout << "student sayHello " << endl ;
    }
   
    void sayGoodbye(void)
    {
      cout << "student sayGoodbye" << endl ;
    }
   
public:
    student();
    virtual ~student() ;
} ;

student::student(void)
{
    fun = &student::sayHello ;
    fun = &student::sayGoodbye ;
    memcpy(_vft, fun, sizeof(int) * 2) ;
}

student::~student(void)
{
    fun = NULL ;
    fun = NULL ;
    _vft = NULL ;
    _vft = NULL ;
}


int main(void)
{
    person thePer ;
    student theStu ;

    person *pPer = NULL ;
    student *pStu = NULL ;
   
    thePer.SayGoodbye() ;
    thePer.SayHello() ;
   
    theStu.SayGoodbye() ;
    theStu.SayHello() ;

    cout << "test pointer" << endl ;

    pPer = &thePer ;
    pPer->SayHello() ;
    pPer->SayGoodbye() ;

    pPer = NULL ;
    pPer = &theStu ;
    pPer->SayHello() ;
    pPer->SayGoodbye() ;

    pStu = &theStu ;
    pStu->SayHello() ;
    pStu->SayGoodbye() ;
   
    system("pause") ;
    return 0 ;
}

[ 本帖最后由 evilknight 于 2009-8-21 22:16 编辑 ]

超然 发表于 2009-8-19 21:51:05

先            顶后看

xusir98 发表于 2009-8-19 22:20:07

向上顶大奇的好东东

evilknight 发表于 2009-8-19 22:23:38

/:L 你们又来BS我了!

Nisy 发表于 2009-8-19 22:50:06

等断网了 我再过来学习 上个网不容易呀 ……

boy 发表于 2009-8-20 10:53:44

膜拜强大的黄牛

evilknight 发表于 2009-8-20 22:00:27

小黑又在BS我了!
页: [1]
查看完整版本: 手工模拟了一下虚表