Problem with STL's std::set container parameter to the operator << ()

Hi,

I have this following code which gives me error when compiling. The problem is happening at the point where I create a const_iterator inside the overloaded insertion operator (i.e) operator << () function. The template argument version of set is not correct I guess. Could anyone please pitch in and make this code working?

#include <iostream>
#include <set>

using namespace std;

class A {
public:
    int _i;
    A(int i) : _i(i) {}
    bool operator < (A a) const { return _i < a._i; }
};

class compA {
public:
    bool operator()(A a1, A a2) const { return (a1._i > a2._i); }
};

template<class T, class C>
std::ostream& operator << (std::ostream& os, const set<T, C>& s) {
    std::set<T, C>::const_iterator itr = s.begin();

    for (int i = 0; i < s.size(); i++) {
        os << *itr++ << " ";
    }

    return os;
}

int main() {
    set<A, less<A> > s1;
    set<A, compA> s2;

    s1.insert(A(9)); s1.insert(A(3)); s1.insert(A(-5)); s1.insert(A(3));
    s2.insert(A(2)); s2.insert(A(1)); s2.insert(A(7));

    cout << s1;
    cout << s2;
}

g++ tells you exactly what to do.

$ g++ iter.cpp
iter.cpp: In function 'std::ostream& operator<<(std::ostream&, const std::set<T, C, std::allocator<_CharT> >&) [with T = A, C = std::less<A>]':
iter.cpp:40:   instantiated from here
iter.cpp:21: error: dependent-name 'std::set::const_iterator' is parsed as a non-type, but instantiation yields a type
iter.cpp:21: note: say 'typename std::set::const_iterator' if a type is meant
iter.cpp: In function 'std::ostream& operator<<(std::ostream&, const std::set<T, C, std::allocator<_CharT> >&) [with T = A, C = compA]':
iter.cpp:41:   instantiated from here
iter.cpp:21: error: dependent-name 'std::set::const_iterator' is parsed as a non-type, but instantiation yields a type
iter.cpp:21: note: say 'typename std::set::const_iterator' if a type is meant

$
template<class T, class C>
std::ostream& operator << (std::ostream& os, const set<T, C>& s)
{
    typename std::set<T,C>::const_iterator itr=s.begin();

    for (int i = 0; i < s.size(); i++) {
  //      os << *itr++ << " ";
    }

    return os;
}

I'd also refactor your loop a bit:

while(itr != s.end())
{
        os << (*itr) << " ";
        itr++;
}

Awesome Corona688!! the code is now compiling :slight_smile:

But this statement, printing the iterator value is giving lot of compilation errors to me. Is that compiling fine for you?