目录
一、初始准备
二、开辟空间与调整数据个数
三、构造函数与析构函数
四、插入与删除数据
五、全部代码
一、初始准备
头文件包含,将标准库直接展开
为了防止与C++库里的命名重名,创建一个命名空间
因为vector可以存储多种类型的数据,所以采用类模板
成员变量,采用三个指针,一个指向开头,一个指向最后一个数据的下一个,最后一个指向容量空间的结尾的下一个
起始地址与最后一个数据地址的下一个
数据个数与空间大小
二、开辟空间与调整数据个数
开辟空间
首先得创建一个变量保存数据个数,以及开辟空间
因为存在初次开空间没有数据,不需要拷贝数据进新空间,所以这里判断一下
再将成员变量指向新空间的相应位置
调整数据个数
调整后的数据个数少于原来数据个数
空间不够,就先扩容,然后多的空间就初始化
三、构造函数与析构函数
默认构造函数,将其全部置空即可
拷贝构造(传统)
对象成员变量交换
首先是开辟与被拷贝对象的一样大小的空间,然后把被拷贝对象的数据拷贝进新空间,最后将其成员变量指向新空间相应的位置
拷贝构造(现代)
首先写一个可遍历的构造函数,并插入数据
然后创建一个临时对象
再交换 两个对象的成员变量
析构函数
首先判断一下是不是有从堆上开辟空间,有就释放,再将成员变量置空
四、插入与删除数据
尾插
如果空间不够,就先扩容
插入数据,数据个数+1
尾删
断言判断一下是否还有数据,然后再数据个数-1
随机位置插入
首先断言判断一下,保证要插入的位置合法
然后判断空间够不够,不够就扩容,同时记住pos的相对位置,要不然扩容后空间的地址的改变了,也就无法插入数据了
然后向后挪动数据,把pos位置的空间空出来,再插入数据,数据个数+1
随机位置删除数据
首先断言判断一下,保证删除的数据位置合法
再往前挪动数据,然后数据个数-1
五、全部代码
#pragma once
#include<iostream>
#include<assert.h>
using namespace std;
namespace Henry
{
template<class T>
class vector
{
public:
typedef T* iterator;
typedef const T* const_iterator;
vector():_start(nullptr),_finish(nullptr),_endofstorage(nullptr)
{}
//拷贝构造
//传统写法
vector(const vector<T>& v)
{
size_t n = v.capacity();
_start = new T[n];
for (size_t i = 0; i < v.capacity(); i++)
{
_start[i] = v._start[i];
}
_finish = _start + v.size();
_endofstorage = _start + v.capacity();
}
//拷贝构造
//现代写法
vector(const vector<T>& v):_start(nullptr),_finish(nullptr),_endofstorage(nullptr)
{
vector<T> tmp(v.begin(), v.end());
swap(tmp);
}
void swap(vector<T>& v)
{
std::swap(_start, v._start);
std::swap(_finish, v._finish);
std::swap(_endofstorage, v._endofstorage);
}
template<class InputIterator>
vector(InputIterator first, InputIterator last) :_start(nullptr),
_finish(nullptr), _endofstorage(nullptr)
{
while (first != last)
{
push_back(*first);
++first;
}
}
//v1 = v3
//现代写法
vector<T>& operator=(vector<T> v)
{
swap(v);
return *this;
}
iterator begin()
{
return _start;
}
iterator end()
{
return _finish;
}
const_iterator begin() const
{
return _start;
}
const_iterator end() const
{
return _finish;
}
const T& operator[](size_t i) const
{
assert(i < size());
return _start[i];
}
T& operator[](size_t i)
{
assert(i < size());
return _start[i];
}
size_t capacity()const
{
return _endofstorage - _start;
}
size_t size()const
{
return _finish - _start;
}
//调整容量
void reserve(size_t n)
{
if (n > capacity())
{
size_t sz = size();
T* tmp = new T[n];
if (_start)
{
for (size_t i = 0; i < sz; i++)
{
tmp[i] = _start[i];
}
delete[] _start;
}
_start = tmp;
_endofstorage = _start + n;
_finish = _start + sz;
}
}
//调整数据个数
void resize(size_t n,const T& val = T())
{
if (n < size())
{
_finish = _start + n;
}
else
{
if (n > capacity)
{
reserve(n);
}
while (_finish != _start + n)
{
*_finish = val;
++_finish;
}
}
}
//随机位置插入
iterator Insert(iterator pos,const T& val = T())
{
assert(pos >= _start);
assert(pos <= _finish);
if (_finish == _endofstorage)
{
size_t len = pos - _start;
reserve(capacity() + 1);
pos = _start + len;
}
iterator tail = end();
while (tail > pos)
{
*(tail) = *(tail - 1);
--tail;
}
*pos = val;
_finish++;
return pos;
}
//随机位置删除
iterator erase(iterator pos)
{
assert(pos >= _start);
assert(pos < _finish);
iterator tail = pos + 1;
while (tail < end())
{
*(tail - 1) = *(tail);
++tail;
}
_finish--;
return pos;
}
//尾插
void push_back(const T& x)
{
//满了
if (_finish == _endofstorage)
{
reserve(capacity() == 0 ? 4 : 2 * capacity());
}
*_finish = x;
_finish++;
}
//尾删
void pop_back()
{
assert(_finish > _start);
_finish--;
}
//析构函数
~vector()
{
if (_start)
{
delete[] _start;
_start = _finish = _endofstorage = nullptr;
}
}
//iterator find(const T& val)
//{
// iterator _start1 = _start;
// while (*_start1 != val && _start1 < _finish)
// {
// _start1++;
// }
// //未找到,返回nullptr
// if (_start1 == _finish)
// {
// return nullptr;
// }
// else
// {
// return _start1;
// }
//
//}
private:
iterator* _start;
iterator* _finish;
iterator* _endofstorage;
};
void test_vector1()
{
vector<int> v1;
v1.push_back(1);
v1.push_back(2);
v1.push_back(3);
v1.push_back(4);
v1.push_back(5);
v1.pop_back();
v1.pop_back();
}
void test_vector2()
{
vector<int> v1;
v1.push_back(1);
v1.push_back(2);
v1.push_back(3);
vector<int> v2(v1);
}
void test_vector3()
{
vector<int> v1;
v1.push_back(1);
v1.push_back(2);
v1.push_back(3);
//v1.Insert(v1.find(2), 20);
//v1.erase(v1.find(3));
}
void test_vector4()
{
vector<int> v1;
v1.push_back(1);
}
}