为什么这个c ++代码不能编译?

时间:2014-02-05 13:05:35

标签: c++ compiler-errors

我正在使用Visual Studio 2012,我收到了很多xmemory0错误。 这是一个通用的树实现。

#include <iostream>
#include <list>

template<class T> class Tree {
public:
    Tree();
    Tree(const T& pNode);
    virtual ~Tree();

    const T& getNode();
    void setNode(const T& pNode);

    void addChild(const Tree<T>& pChild);
    const Tree<T>& getChild(int pIndex);

    const std::list<Tree<T>>* getChildren();
    void printTree(const Tree<T>& pTree, int pLevel=0);
private:
    T node;
    std::list<Tree<T>&>* children;
};

template<class T> Tree<T>::Tree(const T& pNode) : node(pNode), children(nullptr) {
}

template<class T> Tree<T>::Tree() : node(T()), children(nullptr) {
}

template<class T> Tree<T>::~Tree() {
    delete children;
}

template<class T> const T& Tree<T>::getNode() {
    return this->node;
}

template<class T> void Tree<T>::setNode(const T& pNode) {
    this->node=pNode;
}

template<class T> void Tree<T>::addChild(const Tree<T>& pChild) {
    if(this->children==nullptr) {
        this->children=new std::list<Tree<T>&>();
    }

    this->children->push_back(pChild);
}

template<class T> const Tree<T>& Tree<T>::getChild(int pIndex) {
    if(true) {
    }

    return this->children[pIndex];
}

template<class T> void Tree<T>::printTree(const Tree<T>& pTree, int pLevel=0) {
    for(int i=0; i<pLevel; i++) {
        std::cout << "  "; // Print 2 spaces for each level
    }

    std::cout << pTree.node << std::endl;

    if(pTree.children!=nullptr) {
        for(std::list<Tree<T>>::iterator i=pTree.children->begin(); i!=pTree.children->end(); i++) {
            printTree(*i, pLevel+1);
        }
    }
}

template<class T> const std::list<Tree<T>>* Tree<T>::getChildren() {
    return this->children;
}

int main(int argc, char **argv) {
    Tree<int> a, b,c;

    a.setNode(1);
    b.setNode(2);
    c.setNode(3);

    b.addChild(c);
    a.addChild(b);


    a.printTree(a);
}

这是我得到的错误(对不起他们是意大利语):

Errore  1   error C2528: 'pointer': puntatore a riferimento non valido  c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    527 1   Translator

Errore  2   error C2528: 'const_pointer': puntatore a riferimento non valido    c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    528 1   Translator

Errore  3   error C2535: 'Tree<T> &(*std::allocator<_Ty>::address(Tree<T> &) throw() const)': funzione membro già definita o dichiarata c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    561 1   Translator

Errore  4   error C2528: '_Ptr': puntatore a riferimento non valido c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    599 1   Translator

Errore  5   error C2528: '_Ptr': puntatore a riferimento non valido c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    604 1   Translator

Errore  6   error C2528: 'pointer': puntatore a riferimento non valido  c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    700 1   Translator

Errore  7   error C2528: 'const_pointer': puntatore a riferimento non valido    c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    701 1    Translator

Errore  8   error C2535: 'Tree<T> &(*std::_Wrap_alloc<_Alloc>::address(Tree<T> &) const)': funzione membro già definita o dichiarata    c:\program files (x86)\microsoft visual studio 11.0\vc\include\xmemory0 824 1   Translator

Errore  9   error C2528: '_Ptr': puntatore a riferimento non valido c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    890 1   Translator

Errore  10  error C2528: 'abstract declarator': puntatore a riferimento non valido  c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    105 1   Translator

Errore  11  error C2528: 'abstract declarator': puntatore a riferimento non valido  c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    107 1   Translator

Errore  12  error C2528: 'pointer': puntatore a riferimento non valido  c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    122 1   Translator

Errore  13  error C2528: 'const_pointer': puntatore a riferimento non valido    c:\program files (x86)\microsoft visual studio
11.0\vc\include\xmemory0    123 1   Translator

Errore  14  error C2535: 'void std::list<_Ty>::push_front(_Ty)': funzione membro già definita o dichiarata  c:\program files (x86)\microsoft visual studio 11.0\vc\include\list 1276    1   Translator

Errore  15  error C2535: 'void std::list<_Ty>::push_back(_Ty)': funzione membro già definita o dichiarata   c:\program files (x86)\microsoft visual studio 11.0\vc\include\list 1286    1   Translator

Errore  16  error C2535: 'std::_List_iterator<_Mylist> std::list<_Ty>::insert(std::_List_const_iterator<_Mylist>,_Ty)': funzione membro già definita o dichiarata   c:\program files (x86)\microsoft visual studio 11.0\vc\include\list 1319    1   Translator

Errore  17  error C2664: 'std::list<_Ty>::push_back': impossibile convertire il parametro 1 da 'const Tree<T>' a 'Tree<T> ' c:\users\me\documents\visual studio 2012\projects\translator\translator\main.cpp    46  1   Translator

Errore  18  error C2440: 'inizializzazione': impossibile convertire da 'std::_List_iterator<_Mylist>' a 'std::_List_iterator<_Mylist>'  c:\users\me\documents\visual studio 2012\projects\translator\translator\main.cpp    64  1   Translator

Errore  19  error C2678: '!=' binario: non è stato trovato alcun operatore che accetti un operando sinistro di tipo 'std::_List_iterator<_Mylist>'. È anche possibile che non vi siano conversioni accettabili. c:\users\me\documents\visual studio 2012\projects\translator\translator\main.cpp    64  1   Translator

根据Mike Seymour的回答,我将代码更改为:

#include <iostream>
#include <list>

template<class T> class Tree {
public:
    Tree();
    Tree(const T& pNode);
    virtual ~Tree();

    const T& getNode();
    void setNode(const T& pNode);

    void addChild(const Tree<T>* pChild);
    const Tree<T>* getChild(int pIndex);

    const std::list<Tree<T>*>* getChildren();
    void printTree(const Tree<T>* pTree, int pLevel=0);
private:
    T node;
    std::list<Tree<T>*>* children;
};

template<class T> Tree<T>::Tree(const T& pNode) : node(pNode), children(nullptr) {
}

template<class T> Tree<T>::Tree() : node(T()), children(nullptr) {
}

template<class T> Tree<T>::~Tree() {
    delete children;
}

template<class T> const T& Tree<T>::getNode() {
    return this->node;
}

template<class T> void Tree<T>::setNode(const T& pNode) {
    this->node=pNode;
}

template<class T> void Tree<T>::addChild(const Tree<T>* pChild) {
    if(this->children==nullptr) {
        this->children=new std::list<Tree<T>*>();
    }

    this->children->push_back(*pChild);
}

template<class T> const Tree<T>* Tree<T>::getChild(int pIndex) {
    if(true) {
    }

    return this->children[pIndex];
}

template<class T> void Tree<T>::printTree(const Tree<T>* pTree, int pLevel=0) {
    for(int i=0; i<pLevel; i++) {
        std::cout << "  "; // Print 2 spaces for each level
    }

    std::cout << pTree->node << std::endl;

    if(pTree->children!=nullptr) {
        for(std::list<Tree<T>*>::iterator i=pTree->children->begin(); i!=pTree->children->end(); i++) {
            printTree(*i, pLevel+1);
        }
    }
}

template<class T> const std::list<Tree<T>*>* Tree<T>::getChildren() {
    return this->children;
}

int main(int argc, char **argv) {
    Tree<int> a, b,c;

    a.setNode(1);
    b.setNode(2);
    c.setNode(3);

    a.addChild(&b);
    b.addChild(&c);

    a.printTree(&a);
}

但是我收到了这个错误:

错误1错误C2664:'void std :: list&lt; _Ty&gt; :: push_back(_Ty&amp;&amp;)':无法将参数1从const Tree'转换为'Tree&amp;&amp;'第46行

1 个答案:

答案 0 :(得分:-1)

std::list<Tree<T>&>* children;

标准容器无法存储引用类型。从其余代码看,它应该存储Tree<T>个对象。 (如果你想引用居住在其他地方的对象,你必须存储指针而不是引用;但这似乎并非如此)。

您在printTree的声明和定义上都有重复的默认参数,并且在typename中声明std::list<Tree<T>>::iterator i时缺少printTree;您的编译器可能会接受这些错误。