您的位置:首页 > 编程语言 > C语言/C++

C++ 模板实现Vector和双向链表

2017-08-03 10:16 381 查看

模板实现Vector

#define _CRT_SECURE_NO_WARNINGS 1
#include <iostream>
#include <assert.h>
using namespace std;

template<class T>
class Vector
{
public:
Vector()
:_pData(new T[3])
,_size(0)
,_capacity(3)
{}

Vector(size_t n, const T& data)
{
while(n--)
{
Check_capacity();
_pData[_size++] = data;
}
}

Vector(const Vector& v)
:_pData(new T[strlen(v._pData)+1])
,_size(v._size)
,_capacity(v._capacity)
{
strcpy(_pData, v._pData);
}

Vector& operator =(Vector v)
{
Swap(*this, v);
return *this;
}

~Vector()
{
if(_pData != NULL)
{
delete[] _pData;
_pData = NULL;
}
}

void Swap(Vector& v)
{
std::swap(_pData, v._pData);
std::swap(_size, v._size);
std::swap(_capacity, v._capacity);
}

void PushBack(const T& data)
{
Check_capacity();
_pData[_size++] = data;
}

void PopBack()
{
if(_size != 0)
_size--;
}

void PushFront(const T& data)
{
Check_capacity();
for(size_t i = _size; i > 0; i--)
{
_pData[i] = _pData[i-1];
}
_pData[0] = data;
_size++;
}

void PopFront()
{
assert(_size);
for(size_t i = 1; i < _size-1; i++)
{
_pData[i-1] = _pData[i];
}
_size--;
}

void Insert(size_t pos, const T& data)
{
assert(_size && pos>=0 && pos<=_size);
Check_capacity();
for(size_t i = _size; i > pos; i--)
{
_pData[i] = _pData[i-1];
}
_pData[pos] = data;
_size++;
}

void Erase(size_t pos)
{
assert(_size);
assert(_size && pos>=0 && pos<_size);
for(size_t i = pos; i < _size-1; i++)
{
_pData[i] = _pData[i+1];
}
_size--;
}

void Assign(size_t n, const T& data)
{
_size = 0;
while(n--)
{
Check_capacity();
_pData[_size++] = data;
}
}
void Clear()
{
delete[] _pData;
_pData = NULL;
}

T& operator [](size_t index)
{
assert(index < _size);
return _pData[index];
}

const T& operator [](size_t index)const
{
assert(indec < _size);
return _pData[index];
}

T& Front()
{
return _pData[0];
}

const T& Front()const
{
return _pData[0];
}

T& Back()
{
return _pData[_size-1];
}

const T& Back()const
{
return _pData[_size-1];
}

size_t Size()const
{
return _size;
}

size_t Capacity()const
{
return _capacity;
}

bool Empty()const
{
return _size == 0;
}
void ReSize(size_t sz, const T& data = T())
{
if(_size > sz)
{
_size = sz;
}
else if(_size < sz)
{
while(sz > _size)
{
Check_capacity();
_pData[_size++] = T();
}
}
}

void Reserve(size_t n)
{
size_t tmp = _size;
while(_size < n)
{
Check_capacity();
_size++;
}
_size = tmp;
}

void Print()const
{
if(_pData != NULL)
{
for(size_t i = 0; i < _size; i++)
{
cout<<_pData[i]<<"  ";
}
cout<<endl;
}
else
cout<<"NULL"<<endl;
}

void Print_String()const
{
if(_pData != NULL)
{
for(size_t i = 0; i < _size; i++)
{
cout<<(*(_pData+i)).Pri()<<"  ";
}
cout<<endl;
}
else
cout<<"NULL"<<endl;
}

private:
void Check_capacity()
{
if(_size >= _capacity)
{
T* newpData = new T[_size*2];

//1.深拷贝,调用的时赋值运算符重载operator=
for(size_t i = 0; i < _size; i++)
{
newpData[i] = _pData[i];
}
delete[] _pData;
_pData = newpData;
_capacity = _size*2;

////2.浅拷贝,自定义类型设计资源时,可能会出错,思考
//memcpy(_pData, newpData, sizeof(T)*_size);
//_pData = newpData;
}
}

T* _pData;
size_t _size;
size_t _capacity;
};

class String
{
public:
String(const char* str = "")
:_str(new char[strlen(str)+1])
{
strcpy(_str, str);
}

String(const String& s)
:_str(new char[strlen(s._str)+1])
{
strcpy(_str, s._str);
}

String& operator =(String s)
{
swap(_str, s._str);
return *this;
}

char* Pri()const
{
return _str;
}

~String()
{
delete[] _str;
_str = NULL;
}
private:
char* _str;
};

void Test1()
{
Vector <int>v;
v.PushBack(1);
v.PushBack(2);
v.PushBack(3);
v.PushBack(4);
v.Print();

v.PopBack();
v.Print();

v.PushFront(0);
v.Print();

v.PopFront();
v.Print();

v.Insert(0, 5);
v.Print();

v.Erase(0);
v.Print();

cout<<v.Front()<<endl;
cout<<v[1]<<endl;
cout<<v.Back()<<endl;

cout<<v.Size()<<endl;
cout<<v.Capacity()<<endl;
cout<<v.Empty()<<endl;

v.ReSize(2);
v.Print();

v.ReSize(10, 0);
v.Print();

v.Reserve(5);
v.Print();

v.Assign(5, 0);
v.Print();

v.Clear();
v.Print();
}

void Test2()
{
Vector<String> v;
v.PushBack("aaaa");
v.PushBack("bbbb");
v.PushBack("cccc");
v.PushBack("dddd");
v.Print_String();

v.PopBack();
v.Print_String();

v.PushFront("1111");
v.Print_String();

v.PopFront();
v.Print_String();

}

int main()
{
Test1();//内置类型
Test2();//类类型
return 0;
}




模板实现双向链表

(头节点不保存数据,不记作有效节点)

#include <iostream>
#include <assert.h>
using namespace std;

template<class T>
struct Node
{
public:
Node(const T& data = T())
:_Next(NULL)
,_Pre(NULL)
,_data(data)
{}
public:
Node<T>* _Next;
Node<T>* _Pre;
T _data;
};

template<class T>
class List
{
public:
List()
:_pHead(new Node<T>)//构造给出头节点(没有有效data)
{
_pHead->_Next = _pHead;
_pHead->_Pre = _pHead;
}

List(size_t n, const T& data)
:_pHead(new Node<T>)//头节点(没有有效data)
{
while(n--)
{
PushBack(data);
}
}

List(const List& L)
:_pHead(new Node<T>)
{
_pHead->_Next = _pHead;
_pHead->_Pre = _pHead;
Node<T>* tmp = L._pHead->Next;
while(tmp != _pHead)
{
PushBack(tmp->_data);
tmp = tmp->_Next;
}
}

~List()
{
if(_pHead->_Next != _pHead)
{
Clear();
}
delete[] _pHead;
}

void PushBack(const T& data)
{
Node<T>* newEnd = CreatNode(data);
_pHead->_Pre->_Next = newEnd;
newEnd->_Pre = _pHead->_Pre;
_pHead->_Pre = newEnd;
newEnd->_Next = _pHead;
}

void PopBack()
{
if(_pHead->_Next != _pHead)
{
Node<T>* end = _pHead->_Pre;
_pHead->_Pre = end->_Pre;
end->_Pre->_Next = _pHead;
delete[] end;
}
}

void PushFront(const T& data)
{
Node<T>* newFront = CreatNode(data);
_pHead->_Next->_Pre = newFront;
newFront->_Next = _pHead->_Next;
_pHead->_Next = newFront;
newFront->_Pre = _pHead;
}

void PopFront()
{
if(_pHead->_Next != _pHead)
{
Node<T>* tmp = _pHead->_Next;
_pHead->_Next = tmp->_Next;
tmp->_Next->_Pre = _pHead;
delete[] tmp;
}
}

Node<T>* Find(const T& data)
{
Node<T>* tmp = _pHead->_Next;
while(tmp != _pHead)
{
if(tmp->_data == data)
return tmp;
tmp = tmp->_Next;
}
return NULL;
}

void Insert(Node<T>* pos, const T& data)
{
assert(pos);

Node<T>* tmp = CreatNode(data);
tmp->_Next = pos;
tmp->_Pre = pos->_Pre;
pos->_Pre->_Next = tmp;
pos->_Pre = tmp;
}

void Erase(Node<T>* pos)
{
assert(pos);

pos->_Pre->_Next = pos->_Next;
pos->_Next->_Pre = pos->_Pre;
delete[] pos;
}

void Clear()
{
while(_pHead->_Next != _pHead)
{
PopFront();
}
}

void Assign(size_t n, const T& data)
{
Node<T>* tmp = _pHead->_Next;
while(n--)
{
if(tmp != _pHead)
{
tmp->_data = data;
tmp = tmp->_Next;
}
else
{
PushBack(data);
}
}
}

bool Empty()const
{
return _pHead->_Next == _pHead;
}

size_t Size()const
{
size_t size = 0;
Node<T>* tmp = _pHead->_Next;
while(tmp != _pHead)
{
size++;
tmp = tmp->_Next;
}
return size;
}

void Print()
{
Node<T>* tmp = _pHead->_Next;
while(tmp != _pHead)
{
cout<<tmp->_data<<"  ";
tmp = tmp->_Next;
}
cout<<endl;
}

private:
Node<T>* CreatNode(const T& data)
{
return new Node<T>(data);
}

private:
Node<T>* _pHead;
};

int main()
{
List<int> L;
L.PushBack(1);
L.PushBack(2);
L.PushBack(3);
L.PushBack(4);
L.PushBack(5);
L.Print();

L.PopBack();
L.Print();

L.PushFront(10);
L.Print();

L.PopFront();
L.Print();

Node<int>* tmp = L.Find(4);
L.Insert(tmp, 4);
L.Print();

L.Erase(tmp);
L.Print();

cout<<L.Empty()<<endl;
L.Clear();
cout<<"Size = "<<L.Size()<<endl;

L.Assign(10, 5);
L.Print();

return 0;
}


内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: