一个类怎么可能从专门针对自身的模板派生出来?

How is it possible for a class to be derived from a template specialized on itself?

提问人:Luchian Grigore 提问时间:1/29/2012 最后编辑:Raymond ChenLuchian Grigore 更新时间:1/30/2012 访问量:182

问:

我真的不知道如何描述这一点,但这是代码:

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

//....

A a;
a.push_back(a);

它有什么作用,你为什么要这样做?

C++ 模板

评论

0赞 Bo Persson 1/29/2012
默认构造实际上不包含任何 A,所以这很酷。您是否尝试了第二次push_back?std::vector<A>
0赞 Armen Tsirunyan 1/29/2012
stackoverflow.com/questions/4173254/......
0赞 Luchian Grigore 1/29/2012
@BoPersson我现在做到了,而且它有效。
0赞 Bo Persson 1/29/2012
@Luchian - 是的,我期待一个递归副本,但现在意识到递归终止是因为每个新 A 都包含一个比它自己短一个元素的向量。

答:

4赞 Alok Save 1/29/2012 #1

这是奇怪的重复模板模式(CRTP)。
它允许您实现静态多态性

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

评论

0赞 Luchian Grigore 1/29/2012
我只是使用 vector,因为我不想创建一个模板类只是为了证明一个:)点。但你是对的。会调查的。谢谢
0赞 Has QUIT--Anony-Mousse 1/29/2012 #2

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

现在,你为什么要构建一个包含自身的对象,我不知道。但这样做是有原因的。例如,对于单元测试,确保算法能够处理包含循环的集合。幼稚的算法可能会遇到无限循环,从而无法通过单元测试。

1赞 Vlad 1/29/2012 #3

由于它是 s 而不是 s 的向量,因此本身不能包含自身。但这会在调用时向量中添加一个副本。AA*apush_backa

例:

#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=[]
    ]
  ]
]