WEB开发网
开发学院软件开发VC ATL布幔之下的秘密(3) 阅读

ATL布幔之下的秘密(3)

 2006-07-22 22:54:58 来源:WEB开发网   
核心提示: Drive::fun在模板的帮助下,我们可以实现与之相同的行为,ATL布幔之下的秘密(3)(10),程序50.#include <iostream>using namespace std;template <typename T>class Base {public
Drive::fun

在模板的帮助下,我们可以实现与之相同的行为。

程序50.

#include <iostream>
using namespace std;
template <typename T>
class Base {
public:
 void fun() {
  cout << "Base::fun" << endl;
 }
 void doSomething() {
  T* pT = static_cast<T*>(this);
  pT->fun();
 }
};
class Drive : public Base<Drive> {
public:
 void fun() {
  cout << "Drive::fun" << endl;
 }
};
int main() {
 Drive obj;
 obj.doSomething();
 return 0;
}
  

程序的输出和前一个是一样的,所以我们可以用模板来模拟虚函数的行为。

程序中一个有趣的地方为

class Drive : public Base<Drive> {

这表明我们可以将Drive类作为一个模板参数来传递。程序中另外一个有趣的地方是基类中的doSomething函数。

T* pT = static_cast<T*>(this);
pT->fun();

在这里基类的指针被转换为派生类的指针,因为派生类是作为Base类的模板参数传递的。这个函数可以通过指针来执行,由于指针指向了派生类的对象,所以派生类的对象就被调用了。

但是这就有一个问题了:我们为什么要这样做?答案是:这样可以节省虚函数带有的额外开销,也就是虚函数表指针、虚函数表以及节省了调用虚函数所花费的额外时间。这就是ATL中使组件尽可能小、尽可能快的主要思想。

现在,你的脑海中可能会浮现另外一个问题。如果依靠这一开销更少的技术可以模拟虚函数的话,那我们为什么还要调用虚函数呢?我们不应该用这一技术替换所有的虚函数吗?对于这一问题,我可以简短地回答你:不,我们不能用这一技术替换虚函数。

上一页  5 6 7 8 9 10 

Tags:ATL 之下 秘密

编辑录入:爽爽 [复制链接] [打 印]
赞助商链接