vector/List 实现 (顺序表与双向循环链表实现)

来源:互联网 发布:十八掌大数据视频 编辑:程序博客网 时间:2024/04/27 19:58

实现

#include<iostream>#include<string>#include<assert.h>#include <cstring>using namespace std;struct TrueType{};struct FalseType{};template <class T>struct IsPoD{  typedef  struct FalseType ispod;};template<>struct IsPoD<int>{  typedef  struct TrueType ispod;};template<>struct IsPoD<char>{   typedef struct TrueType ispod;};template<> struct IsPoD<float>{   typedef  struct TrueType ispod;};template<> struct IsPoD<long>{   typedef  struct TrueType ispod;};template <class T>class SeqList { public:         SeqList()           :_a(nullptr),_size(0),_capacity(0)        {}        SeqList(const SeqList<T>& s)        {            allocate(_a,s._a,s._size,s._size,typename IsPoD<T>::ispod());           }        SeqList& operator=(SeqList<T>object)        {            std::swap(object._a,_a);            _size = object._size;            _capacity = object._capacity;        }        ~SeqList()        {            delete []_a;        }        void PushBack(const T& x);        void PopBack();         void Insert(size_t pos, const T& x);         void Erase(size_t pos);         T& operator[](size_t pos);         void Print();protected :        void allocate(T*&dest,T*src,size_t N,size_t size,struct TrueType)        {            dest = new T[N];//N代表要申请多少个元素的空间大小,size代表src共有多少个元素             memmove(dest,src,size*sizeof(T));        }#if 1        void allocate(T*&dest,T*src,size_t N,size_t size,struct FalseType)        {            dest = new T[N];            for(int i=0;i<size;++i)            {                dest[i]=src[i];            }        }#endif        void CheckCapicity()        {            if(_size==_capacity)            {               T * tmp=nullptr;               allocate(tmp,  _a,    _size*2+5,   _size, typename  IsPoD<T>::ispod());                  delete [] _a;               _a = tmp;            }        }private:         T* _a;         size_t _size;         size_t _capacity; }; template<class T>void SeqList<T>::PushBack(const T&x){    CheckCapicity();    _a[_size++] = x;}template<class T>void SeqList<T>::PopBack(){    this->_size--;}template<class T>void SeqList<T>::Insert(size_t pos,const T&x){    CheckCapicity();    for(size_t i=this->_size-1;i >=pos ; --i)    {        _a[i+1] = _a[i];    }    _a[pos]=x;    ++_size;}template<class T>void SeqList<T>::Erase(size_t pos){    for(size_t i=pos;i<this->_size;++i)    {        _a[i]=_a[i+1];    }    this->_size--; }template<class T>T& SeqList<T>::operator[](size_t pos){     assert(pos<_size);     return  _a[pos];}template<class T>void SeqList<T>::Print(){    for(int i=0;i<this->_size;++i)    {        cout<<this->_a[i]<<endl;    }}#if 1// 带头节点的双向循环链表--思考结构的优势 template <class T>struct ListNode {        ListNode(const T&x=T())        {            _data = x;            _next = nullptr;            _prev = nullptr;        }        ~ListNode()        {}        T _data;         ListNode* _next;         ListNode* _prev; }; template<class T> class List {         typedef ListNode<T> Node; public:         List()            :_head(nullptr)        {}        List(const List& l)        {             allocate(_head,l._head);        }        List& operator=(const List l)        {            std::swap(l._head,_head);            return *this;        }        ~List()         {            Node * pCur = _head;            Node * prev = nullptr;            while(prev!=_head) // 哇 写的完美 nullptr 也处理掉了 太开心了,还只进行了一次内存引用 呀咯 无敌勒             {                prev = pCur; // 这个赋值 要处理 只有一个节点的情况                pCur = pCur -> _next;                delete  prev;                prev = pCur;            }        }        void PushBack(const T& x);         void PopBack();        void PushFront(const T& x);         void PopFront();        void Insert(Node* pos, const T& x);         void Erase(Node* pos);         void Print();protected:        void allocate(Node*&Dest,Node*Src)        {            if(Dest==nullptr||Dest == Src)                return ;            Node * pCur = nullptr;            Node * prev =nullptr;            Dest = pCur = prev = new Node(Src);            Src = Src->_next;            while(Src)            {                pCur = pCur->_next = new Node(Src);                pCur->_prev = prev;                prev = pCur;                Src = Src->_next;            }            pCur->_next = Src;            Src ->_prev = pCur;        }private:         Node* _head; };template<class T>void List<T>::PushBack(const T&x){    if(_head==nullptr)    {        _head = new Node(x);        _head->_prev = _head;        _head->_next = _head;        return ;    }    Node * prev = this->_head->_prev;    Node * pCur = prev->_next = new Node(x);    pCur ->_prev = prev;    pCur ->_next = _head;    _head ->_prev = pCur;}template<class T>void List<T>::Print(){    if(_head)    {        Node * pCur = _head;        while(pCur->_next!=_head)        {           cout<<pCur->_data<<" ";           pCur = pCur->_next;        }        cout<<pCur->_data;    }    cout<<endl;}template<class T>void List<T>::Erase(Node*pos){    assert(pos);    Node * prev = pos->_prev;    Node * pnext = pos->_next;    prev->_next = pnext;    pnext->_prev = prev;    delete pos;    if(_head==pos)        _head = pnext;}template<class T>void List<T>::Insert(Node*pos,const T&x){    assert(pos);    Node * prev = pos->_prev;    Node * pCur = prev->_next = new Node(x);    pos->_prev = pCur;    pCur->_prev = prev;    pCur->_next = pos;}template<class T>void List<T>::PushFront(const T&x){    PushBack(x);}template<class T>void List<T>::PopBack(){    assert(_head);    if(_head==_head->_next)    {        delete _head;        _head = nullptr;    }    else    {        Node * del = this->_head->_prev;        Node * prev = del->_prev;        prev->_next = _head;        _head->_prev = prev;        delete del;    }}template<class T>void List<T>::PopFront(){    assert(_head);    if(_head==_head->_next)    {        delete _head;        _head = nullptr;        return ;    }    Node*Pnext = _head->_next;    Node*Prev=Pnext->_prev = _head->_prev;    Prev->_next = Pnext;    Pnext->_prev = Prev;    delete _head;    _head = Pnext;}void TestSeqList() {         SeqList<string> s2;         s2.PushBack("aaaaaaaaaaaaaaaaaaa");         s2.PushBack("bbb");         s2.PushBack("ccc");         s2.PushBack("ddd");         s2.Print();          SeqList<int> s3;         s3.PushBack(1);        s3.PushBack(2);        s3.PushBack(3);        s3.PushBack(4);        s3.Print(); } void TestList(){    List<string> s1;    s1.PushBack("1111");    s1.PushBack("2222");    s1.PushBack("3333");    s1.PushBack("4444");    s1.PushBack("5555");    s1.PushBack("6666");    s1.Print();    s1.PopBack();    s1.PopFront();    s1.PopBack();    s1.PopBack();    s1.PopFront();    s1.PopFront();    s1.Print();}int main(){   // TestSeqList();    TestList();    return 0;}