I'm trying to implement a linked list class in a manner similar to STL. Everyithing seems to work fine, but when I try to implement an output operator to let me see what is inside the collection quickly, it starts acting wierd. Note that I use the iterator inside the linked list class in several methods, as well as in main to iterate through the list. However, when I try a simple generic output operator like

template<typename T>
std::ostream& operator<<(std::ostream& out, list<T> lt){
  for(list<T>::iterator i=lt.begin(); i!=lt.end(); ++i) //this line gives me errors
    out << *i << ' ';
  out << std::endl;

I replace the for loop with this line list<T>::iterator i; , and gcc gives me an error, saying that there is a semicolon missing before the i.

The exact same code in main (with all T replaced by int or double or whatever I was using) works flawlessly.

Here's my source:

template<typename T>
class list{
	class listNode{
		listNode* prev;
		listNode* next;
		T data;
		listNode(listNode* newp=NULL, listNode* newn=NULL, const T& newd=T()) :prev(newp), next(newn), data(newd) {}
	listNode* head;
	listNode* tail;
	int s;
	class iterator{
		friend class list;
		listNode* ptr;
		iterator(listNode& lnr) : ptr(&lnr) {}
		iterator(listNode* p=NULL) : ptr(p) {}
		iterator& operator++() { ptr=ptr->next; return *this; }//pre
		iterator operator++(int a) { iterator retval = *this; ++*this; return retval; }//post
		iterator& operator--() { ptr=ptr->prev; return *this; }//pre
		iterator operator--(int a) { iterator retval = *this; --*this; return retval; }//post
		T& operator*() const { return ptr->data; }
		bool operator==(const iterator& rhs) const { return ptr == rhs.ptr; }
		bool operator!=(const iterator& rhs) const { return ptr!=rhs.ptr; }
	iterator begin() const { return iterator(head->next); }
	iterator end() const { return iterator(tail); }

template<typename U>
std::ostream& operator<<(std::ostream& out, const list<U>& lt) {
	list<U>::iterator lti;   //<----this line gives error, thinks semicolon is missing
	//for(lti=lt.begin(); lti!=lt.end(); ++lti){
	//	out << *lti << ' ';
	//out << std::endl;

Of course, I have all the typical methods you would expect from a list class, like push_front, push_back, pop_front, pop_back, insert(iterator), remove(iterator), but I didn't include them here because they all work perfectly.

So could anyone tell me why this works -

int main(int argc, char** argv)
	list<int> listOfInt;
	for(int i=0; i<10; ++i)
	for(list<int>::iterator iter=listOfInt.begin(); iter!=listOfInt.end(); ++iter)
		std::cout << *iter << ' ';
	return (EXIT_SUCCESS);

and my output operator doesnt?

I love you! Thank you so much! I never thought it would work like that! Just had to put typename list<T>::iterator instead of just list<T>::iterator .


Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.