破晓 发表于 2015-1-16 13:55:19

C++静态绑定与动态绑定

目前我参与的项目中使用了大量的接口调用,大量的继承(多重继承,多重派生等),其中的大部分都是使用了C++语言的动态绑定特性.既然有动态绑定,哪就相应的肯定有静态绑定,今晚复习了下这个特性.静态绑定与动态绑定静态绑定又名前期绑定(early binding),绑定的是对象的静态类型发生在编译期.动态绑定又名后期绑定(late binding),绑定的是对象的动态类型,发生在运行期.简单的说就是:静态绑定在编译完成后已经确定,动态绑定则需要在运行的时候才确定.考虑如下继承:class B{
public:
    void testA(){printf("class B testA()\n");};
    virtual void testB(){printf("class B testB()\n");};
};

class D:public B{
public:
    void testA(){printf("class D testA()\n");};
    virtual void testB(){printf("class D testB()\n");};
};

int main(int argc, const char * argv[])
{

    // insert code here...
   
    D x;
    B* pB = &x;
    D* pD = &x;
    printf("testing non-virturl\n");
    pB->testA();
    pD->testA();
    printf("testing virturl\n");
    pB->testB();
    pD->testB();
    return 0;
}运行后输出如下:testing non-virturl
class B testA()
class D testA()
testing virturl
class D testB()
class D testB()pB,pD虽然都指向派生类D,但是调用non-virtual函数(非虚成员函数)的时候pB调用到基类B的定义.调用virtual函数(虚函数)的时候则均是调用到派生类D的定义.原因在于:非虚函数属于静态绑定,所以类B或者D 指针调用非虚函数的时候 均是调用到自身的定义.虚函数属于动态绑定,无论指针类型是基类B还是派生类D,调用到的都取决于调用的那个对象的类型.往后C++编程中应当避免
[*]重新定义非虚成员类
[*]多重继承中的指针频繁转换
[*]接口基类不应该有非虚函数(也就是全部设置位纯虚函数)
这篇日志系Effective C++读书笔记,参考其中第36,37条款.
本文来自:http://shadowkong.com/archives/1818
页: [1]
查看完整版本: C++静态绑定与动态绑定