#ifndef _CLLIST_H
#define _CLLIST_H

#include "list.h"

namespace uprm_icom4035 {
  
  template <typename Item>
  class cl_list_node {
  public:
    Item data;
    cl_list_node *next;
    cl_list_node *prev;
  };

  template <typename Item>
  class CLList;

  template <typename Item>
  class CLLIterator : public Iterator<Item> {
    friend class CLList<Item>;
    
  public:
    virtual bool has_data() const;
    virtual void next();
    virtual void reset();
    virtual Item& get_data() const;
    virtual void prev();
    
  private:
    CLLIterator(cl_list_node<Item> *hdr, cl_list_node<Item> *tail);
    cl_list_node<Item> *hdr;
    cl_list_node<Item> *tail;
    cl_list_node<Item> *curr;
  };

  template <typename Item>
  class CLList : public list<Item> {
  public:
    
    CLList();
    CLList(const CLList<Item>& L);
    ~CLList();
    const CLList<Item>& operator=(const CLList<Item>& L);
    
    virtual Iterator<Item> *find(const Item& obj) const ;
    virtual Iterator<Item> *first() const;
    virtual void insert(const Item& obj);
    virtual bool erase(const Item& obj);
    virtual size_type size() const;
    virtual bool is_empty() const;
    virtual void make_empty();
    virtual void print_list(ostream& out) const;

  private:
    cl_list_node<Item> *header;
  };

}

#endif
