2011-10-04 38 views
0

我有一个模板化的Stack类,内部实现了vector。模板类上的C++操作符重载

这是我(简化)TStack.h的内容:

#include <vector> 
#include <iostream> 

template<typename T> class TStack; 
template<typename T> TStack<T> operator+(const TStack<T> &s1, const TStack<T> &s2); 

template<typename T> 
class TStack { 
    friend TStack<T> operator+<>(const TStack<T> &s1, const TStack<T> &s2); 
    private: 
     std::vector<T> items; 
    public: 
     void printAll() { 
      std::cout << "The content of the stack is: "; 
      typename std::vector<T>::iterator it; 
      for(it = items.begin(); it < items.end(); it++) { 
       std::cout << *it << " "; 
      } 
      std::cout << std::endl; 
     } 
}; 

template<typename T> 
TStack<T> operator+(const TStack<T> &s1, const TStack<T> &s2) { 
    TStack<T> result = s1; 
    typename std::vector<T>::iterator it; 
    //below is line 41 
    for(it = s2.items.begin(); it < s2.items.end(); it++) { 
     result.items.push_back(*it); 
    } 
    return result; 
} 

这是我(简化)主类:

#include <iostream> 
#include "TStack.h" 

using namespace std; 

int main(int argc, char *argv[]) { 
    TStack<int> intStack; 
    intStack.push(4); 

    TStack<int> secondIntStack; 
    secondIntStack.push(10); 

    cout << "Addition result: " << endl; 
    //below is line 27 
    TStack<int> result = intStack + secondIntStack; 
    result.printAll(); 
    return 0; 
} 

这是编译的结果:

In file included from main.cpp:2: 
TStack.h: In function ‘TStack<T> operator+(const TStack<T>&, const TStack<T>&) [with T = int]’: 
main.cpp:27: instantiated from here 
TStack.h:41: error: no match for ‘operator=’ in ‘it = s2->TStack<int>::items.std::vector<_Tp, _Alloc>::begin [with _Tp = int, _Alloc = std::allocator<int>]()’ 
/usr/include/c++/4.4/bits/stl_iterator.h:669: note: candidates are: __gnu_cxx::__normal_iterator<int*, std::vector<int, std::allocator<int> > >& __gnu_cxx::__normal_iterator<int*, std::vector<int, std::allocator<int> > >::operator=(const __gnu_cxx::__normal_iterator<int*, std::vector<int, std::allocator<int> > >&) 
make: *** [main.exe] Error 1 

我不知道错误信息的含义是什么。

在运算符+函数中,我使用了相同的方式来获取printAll()中的迭代器,但它在operator +函数内部不能正常工作。 我知道我可以避免在运算符+函数中使用迭代器,但我只是好奇如何解决这个问题。

回答

5

使用const_iterator代替iterator

typename std::vector<T>::const_iterator it; 

因为s1是一个const对象。因此s1.items也将是const对象,这意味着s1.items.begin()将返回const_iterator,而不是非const iterator


更好地执行运营商+()

可以提高operator+()实施。而是采用了手动循环,push_back功能,您可以使用insert功能:

template<typename T> 
TStack<T> operator+(const TStack<T> &s1, const TStack<T> &s2) { 
    TStack<T> result(s1); //use direct copy-initialization 
    result.insert(result.end(), s2.begin(), s2.end()); 
    return result; 
} 

它完全避免了在哪,你在你的代码面对iterator的问题。


更多更好的执行操作的+()

如果您接受值的第一个参数,而不是常引用,那么就更好了:

template<typename T> 
TStack<T> operator+(TStack<T> s1, const TStack<T> &s2) { 
    s1.insert(s1.end(), s2.begin(), s2.end()); //s1 is a copy, after all! 
    return s1; 
} 

作为第一参数是副本本身,您不需要明确创建名为result的局部变量。您只需将s2添加到s1并返回s1即可。

+1

感谢您的帮助! – Hery

3

您不能将常量迭代器(s2.items.begin())分配给非常量迭代器。 使用

typename std::vector<T>::const_iterator it; 
+0

谢谢你的回答,但我必须把接受的答案给予纳瓦兹,因为他回答了1分钟快哈哈哈... – Hery

+0

没问题,这就是如何运作 – stijn