Error with T :: iterator, where the template parameter T can be a vector <int> or list <int>

I am trying to write a function to print the representation of common STL containers (vector, list, etc.). I gave the function a template parameter T, which, for example, could represent a vector. I am having problems getting an iterator of type T.

vector<int> v(10, 0); repr< vector<int> >(v); 

...

 template <typename T> void repr(const T & v) { cout << "["; if (!v.empty()) { cout << ' '; T::iterator i; for (i = v.begin(); i != v.end()-1; ++i) { cout << *i << ", "; } cout << *(++i) << ' '; } cout << "]\n"; } 

...

 brett@brett-laptop :~/Desktop/stl$ g++ -Wall main.cpp main.cpp: In function 'void repr(const T&)': main.cpp:13: error: expected ';' before 'i' main.cpp:14: error: 'i' was not declared in this scope main.cpp: In function 'void repr(const T&) [with T = std::vector<int, std::allocator<int> >]': main.cpp:33: instantiated from here main.cpp:13: error: dependent-name 'T::iterator' is parsed as a non-type, but instantiation yields a type main.cpp:13: note: say 'typename T::iterator' if a type is meant 

I tried "typename T :: iterator" as the compiler suggested, but got only a more cryptic error.

Edit: Thanks for the help guys! Here is the working version for those who want to use this feature:

 template <typename T> void repr(const T & v) { cout << "["; if (!v.empty()) { cout << ' '; typename T::const_iterator i; for (i = v.begin(); i != v.end(); ++i) { if (i != v.begin()) { cout << ", "; } cout << *i; } cout << ' '; } cout << "]\n"; } 
+6
c ++ stl templates repr
source share
2 answers

You need typename to tell the compiler that ::iterator should be a type. The compiler does not know what this type is, because it does not know what T is until you instantiate the template. For example, it may also refer to some element of static data. This is your first mistake.

The second mistake is that v is a reference to const . So instead of ::iterator you should use ::const_iterator . You cannot request a persistent container for a non-constant iterator.

+18
source share

Change T::iterator i; on typename T::const_iterator i; because ::iterator is of type T and v is const & .

Before a qualified dependent type, you need typename . Without typename there is a C ++ parsing rule that states that qualified dependent names should be parsed as non-types , even if this leads to a syntax error.

typename indicates that the subsequent name should be considered as a type. Otherwise, the names are interpreted to mean non-types.

+3
source share

All Articles