重载和double dispatch

1. 函数重载


参数表不相同(参数型别不一样或者参数数目不一样)的两个或多个函数能够构成重载函数,编译器不能经过返回类型来判断几个函数是否为重载函数
1> 参数型别不一样: 注意: 这里的类别不只指基本类型(short、int、long、char、float、double 基本类型的指针等),还包括复杂类型(父类类,各子类)(与double dispatch有关联)
2> 参数数目不一样


重载函数调用的优先级以下:
1> 准确匹配,实参类型与形参类型彻底匹配。
2> 类型提高,好比 bool to int, int to unsigned int (指针类型没有类型提高一说,bool * 和int * 始终是不一样类型,这在理解static_cast, reinterprete_cast不一样时是同样的)
     例: 
           void fun(int); // bool b; fun(b);  编译经过 
           void fun(bool); // int i; fun(i); 编译error  
           void fun(int*); // bool b; fun(&b);  编译error
3> 标准类型转换,好比 int to double, double to int, 子类提高为父类
     例: 
           void fun(double); // int b; fun(b);  编译经过 
           void fun(int); // double i; fun(i); 编译经过

4> 用户自定义转换 // 待解
5> 不定数量形参(...) // 待解


class A { };c++

class AA : public A {}设计模式

class B {函数

public: this

    void fun(A& a) {}spa

    void fun(AA& a1) {}.net

};设计


int main(void)指针

{对象

    A* a = new A;blog

    A* a1 = new AA;

    AA* aa = new AA;

    B b;

    b.fun(*a); // 会调用 void fun(A& a) {}

    b.fun(*a1); // 会调用 void fun(A& a) {}  这就是单dispatch,没法识别a1真正的类型,c++不支持double dispathc

    b.fun(*aa);  // 会调用 void fun(AA& a) {} // aa是AA类的实例。

}




2. Double Dispatch(双分派)   
     visitor模式采用了Double Dispatch方式
     双分派就是根据运行时多个对象的类型肯定方法调用的过程。c++语言只支持静态多分派和动态的单分派,可是能够利用设计模式能够实现Double Dispatch


     静态分派(Static Dispatch,静态多态---重载),发生在编译时期,分派是根据静态类型信息发生的,方法重载就是静态分派
     动态分派(Dynamic Dispatch,动态多态---虚函数),发生在运行时期,动态分派动态地置换掉某个方法

     举例: 对vector<A *>排序, 每一个A子类对象都要实现compare函数,用于this和另外一个对象的比较

     class A {

        public: 

              virtual bool compare(A* a) = 0;

      } 

      此时, 每一个子类的compare函数里都须要switch case来判断到底和哪一种子类对象进行比较,这就是一种Double Dispatch。

      改进:使用子类重载来消除switch case,父类也须要改进。

      class A {

        public: 

              bool compare(A* a)  { a->compare(*this); }  // *this取得了子类对象   动态多态

              virtual 

      }

      class A1 : public A {

      public: 

             virtual bool compare(A2& a) { ,,. }  // 静态多态

      }

      

     class A2 : public A {

      public: 

             virtual bool compare(A1& a) { ,,. }   // 静态多态

      }

     这里假设只有A1和A2两个子类,若是再加一个子类A3,则A1 A2子类中都要增长一个compare函数virtual bool compare(A3& a) ,用于和新增对象的比较。这也是visitor模式最主要的缺点


参考:

http://blog.csdn.net/seizef/article/details/5332297

http://blog.163.com/very_fyy/blog/static/22521685201063044030549/