2012-01-29 56 views
5

我真的不知道该怎么形容这一点,但是这是代码:如何从专用于自身的模板派生类?

class A : public std::vector<A> 
{ 
}; 

//.... 

A a; 
a.push_back(a); 

它能做什么和你为什么要这么做?

回答

4

这是curiously recurring template pattern(CRTP)
它允许你实现静态多态性

但是,使用std::vector作为基类是不好的做法,因为它没有虚拟析构函数。

+0

我刚使用过vector,因为我不想创建一个模板类来证明一个观点:)。但你是对的。将研究它。谢谢 – 2012-01-29 15:37:58

0

子类是终止泛型。该向量只能包含A类型的对象,而不能是任意向量。

现在,你为什么要建立一个包含自己的对象我做不是知道。但有理由这样做。例如,对于单元测试,要确保算法能够处理包含循环的集合。一个天真的算法可能会陷入无限循环,因此单元测试失败。

1

由于它是A s的矢量而不是A* s,因此a本身不能包含它自己。但是push_back会在呼叫时向该向量添加a的副本。

例子:

#include <vector> 
#include <iostream> 
using namespace std; 
class A : public std::vector<A> 
{ 
    public: 
     void print(int level=0){ 
      for (int i=0;i<level;i++) cout<<" "; 
      cout << "0x" << hex << (unsigned int)this << "=["; 
      if (size()){ 
       cout << endl; 
       for (int i=0; i<size(); i++) 
        (*this)[i].print(level+1); 
       for (int i=0;i<level;i++) cout<<" "; 
      } 
      cout <<"]"<<endl; 
      if(!level) cout << endl; 
     } 

}; 

int main(){ 
    A a; 
    for (int i=1;i<=3;i++){ 
     a.push_back(a); 
     a.print(); 
    } 
    return 0; 
} 

和输出:

0xbff4fa20=[ 
    0x9ec2008=[] 
] 

0xbff4fa20=[ 
    0x9ec2018=[] 
    0x9ec2024=[ 
    0x9ec2038=[] 
    ] 
] 

0xbff4fa20=[ 
    0x9ec2048=[] 
    0x9ec2054=[ 
    0x9ec20a0=[] 
    ] 
    0x9ec2060=[ 
    0x9ec2080=[] 
    0x9ec208c=[ 
     0x9ec2008=[] 
    ] 
    ] 
] 
相关问题