3
votes

can someone explain what is the mention of this error:

conversion from 'std::vector<int, std::allocator<int> >::const_iterator {aka __gnu_cxx::__normal_iterator<const int*, std::vector<int, std::allocator<int> > >}' to non-scalar type 'std::vector<int, std::allocator<int> >::iterator {aka __gnu_cxx::__normal_iterator<int*, std::vector<int, std::allocator<int> > >}' requested

given the following class:

#include <vector>
#include <iostream>

using std::vector;
using std::ostream;

template<class T>
class Gen {
    vector<T> array;
public:
    explicit Gen(int size);
    template<class S>
    friend ostream& operator<<(ostream& os, const Gen<S>& g);
};

template<class T>
Gen<T>::Gen(int size) {
    for (int i = 0; i < size; i++) {
        this->array.push_back(T());
    }
}

template<class T>
ostream& operator<<(ostream& os, const Gen<T>& g) {
    for (typename vector<T>::iterator it = g.array.begin(); it != g.array.end();
            it++) { // ****** error ********
        os << *it << " ";
    }
    return os;
}

int main() {
    Gen<int> g(3);
    std::cout << g << std::endl;
}

how can I fix that?

1
@MohammadKanan I can't do it without defines new class of Iterator?AskMath
Use typename vector<T>::const_iterator instead, that should work.Eljay
It's dense, but read the error message carefully. It's complaining about converting std::vector<int>::const_iterator to std::vector<int>::iterator. That's a problem, because iterator allows you to assign to the thing it points at, but const_iterator does not. The container is const, so you can't modify its elements. With practice these error messages become easier to decipher.Pete Becker

1 Answers

6
votes

You are passing in a const Gen<T> to operator<<. This means when you call g.array.begin() you are invoking the const overload of begin, which returns a const_iterator:

const_iterator begin() const noexcept;

and then you try to assign it to a vector<T>::iterator, which causes the compiler error. You can fix this like this:

auto it = g.array.begin()

which tells the compiler to deduce the correct type for it.