错误:'e'不是类,命名空间或枚举

时间:2016-10-04 07:47:06

标签: c++ templates stl iterator

我正在尝试重载运算符<<仅用于打印STL容器的每两个元素。但是我在编译期间出错:

error: 'e' is not a class, namespace, or enumeration

这是我的代码:

#include <iostream>
#include <vector>

template<typename T>
std::ostream& operator<<(std::ostream &out, T const &e){
    for(e::iterator it = e.begin(); it != e.end(); it = it + 2){
        out << *it << " ";
    }
    return out;
} 

int main(){
    std::vector<int> v;
    for(int i= 0; i < 10; i++){
        v.push_back(i);
    }

    std::cout << v;
    return 0;
}

1 个答案:

答案 0 :(得分:4)

这里有两个问题。

一个是e::iterator。您无法通过对象访问成员类型,您需要使用该类型。相反,你应该使用auto it = e.begin()。如果您不能使用C ++ 11,那么您需要使用

typename T::const_iterator it = e.begin()

需要typename,因为该名称取决于模板参数,并且需要const_iterator而非iterator,因为参数标记为const

然而,你更令人震惊的错误是首先使这个过载。

template<typename T>
std::ostream& operator<<(std::ostream &out, T const &e){

这声明任何类型std::ostream输出重载。这肯定会让您头痛,当然,如果您修复了第一个错误,在尝试输出" "时会出现模糊的函数调用错误:

main.cpp:7:20: error: use of overloaded operator '<<' is ambiguous (with operand types '__ostream_type' (aka 'basic_ostream<char, std::char_traits<char> >') and 'const char [2]')
        out << *it << " ";
        ~~~~~~~~~~ ^  ~~~

如果你真的想让它与每个标准库容器一起使用,我想你会检查T::iterator之类的东西是否存在,并且只有在启用了过载的情况下才能启用。像这样:

template<typename T, typename = typename T::iterator>
std::ostream& operator<<(std::ostream &out, T const &e){
    for(auto it = e.begin(); it != e.end(); it = it + 2){
        out << *it << " ";
    }
    return out;
} 

Live demo