今天看到Pointer-to-Member Functions一节,说到指向虚函数、多继承条件下的成员函数的函数指针时,给出了stroustrup的方案:添加一个结构以记录指针间的区别,对普通成员函数而言,取得的是成员函数的地址,而虚函数则得到该函数在虚函数表中的序号。而后又提到microsoft的一个方案,即使用thunk函数(这个词不是很确定它的翻译,虽然意思能够理解,大概类似于“桩”函数之类):对于指向普通的成员函数的指针,与原来无差别;对于虚函数指针,得到的则是一个称为“vcall”的thunk函数的指针,由该thunk函数负责实际的虚函数调用工作。它的方案仍然使用stroustrup引入的结构,但去除了结构中的index(指向虚函数表的索引值,同时也是判定是否是虚函数指针的标志),因而减小了内存消耗;同时减轻了每次通过函数指针调用时的一个附加判断(判断是否是虚函数指针):现在的普通成员函数调用没有额外开销(overhead);而虚函数调用则通过一个间接函数调用替换了判断,从开销上来说基本与原来持平。
这其实是典型的“通过引入一个间接层解决问题”的例子。与OO思想中的“任何问题都可以通过引入一个间接层而解决”的概念不谋而合(这个例子本身虽然是解决OO实现中遇到的问题,但解决方案本身并不是OO相关的)。可见思想是相通的,OO思想不仅仅可以应用于OO领域,在其它领域也同样有可能有所作为。