vector容器模拟实现及使用——C++

目录

一、vector基本概念

二、构造函数

三、assign()赋值函数

四、empty()函数

五、capacity()函数及size()函数

六、resize()函数

七、push_back()尾插函数

八、pop_back()尾删函数

九、insert()插入函数

十、erase()删除函数

十一、clear()清空函数

十二、at()元素访问函数

十三、front(),back()获取头尾元素

十四、swap()交换函数

十五、reserve()预开辟空间函数

十六、begin(),end()迭代器

十七、运算符重载

十八、析构函数

十九、vector全部模拟实现源码

二十、main函数测试用例


一、vector基本概念

1.vector数据结构和数组非常相似,也称为单端数组,也就是顺序表。

当然也可以用链表实现

2.vector是动态的模板顺序表,可以动态扩展

3。扩展是开辟新的空间,将原有数据拷贝过来,并释放旧空间

创建准备,定义专有的命名空间

#include<iostream>
using namespace std;
namespace mxyvector
{
	template<typename T>
	class mvector
	{
		T*_start;
		T*_end;//用指针记录数据元素个数,减去_start即为元素个数
		T*_endofstorage;//记录容量

二、构造函数

函数类外书写,每个函数前都要声明模板

    template<typename T>
	mvector<T>::mvector()//无参构造
	{
		this->_start = this->_end = this->_endofstorage = NULL;
	}
	template<typename T>
	mvector<T>::mvector(T*begin, T*end)//迭代器传参,T*即为iterator
	{
		size_t len = end - begin;//拷贝所需的空间长度
		this->reserve(len);
		for (size_t i = 0; i < len; i++)
		{
			this->_start[i] = begin[i];
			this->_end++;
		}
	}
	template<typename T>
	mvector<T>::mvector(size_t n, T elmn)//元素传参构造
	{
		this->reserve(n);
		for (size_t i = 0; i < n; i++)
		{
			this->_start[i] = elmn;
			this->_end++;
		}
	}
	template<typename T>
	mvector<T>::mvector(const mvector & mvec)//拷贝构造
	{
		this->reserve(mvec.capacity());
		for (size_t i = 0; i < mvec.size(); i++)
		{
			this->_start[i] = mvec._start[i];
			this->_end++;
		}
	}

三、assign()赋值函数

    template<typename T>
	void mvector<T>::assign(T*begin, T* end)
	{
		this->clear();//先清除原有数据
		size_t len = end - begin;
		this->reserve(len);//空间开辟
		for (size_t i = 0; i < len; i++)
		{
			this->_start[i] = begin[i];
			this->_end++;
		}
	}
	template<typename T>
	void mvector<T>::assign(size_t n, T elmn)
	{
		this->clear();
		this->reserve(n);
		for (size_t i = 0; i < n; i++)
		{
			this->_start[i] = elmn;
			this->_end++;
		}
	}

四、empty()函数

    template<typename T>
	bool mvector<T>::empty()
	{
		return this->_start == this->_end;//如果头尾指针相同,则未存任何元素,为空
	}

五、capacity()函数及size()函数

    template<typename T>
	size_t mvector<T>::capacity()const
	{
		return this->_endofstorage - this->_start;//地址相减得长度
	}
	template<typename T>
	size_t mvector<T>::size()const
	{
		return this->_end - this->_start;
	}

六、resize()函数

设定指定大小的空间

    template<typename T>
	void mvector<T>::resize(size_t num)
	{
		if (num <= this->size())//指定任意大小空间
		{
			this->_end = this->_start + num;//重新指定尾指针
			this->_endofstorage = this->_start + num;
			return;
		}
		if (num > this->capacity())//扩大开辟空间
			this->reserve(num);
	}
	template<typename T>
	void mvector<T>::resize(size_t num, T elmn)//则个加个初始化赋值
	{
		if (num <= this->size())
		{
			this->_end = this->_start + num;
			this->_endofstorage = this->_start + num;
			return;
		}
		if (num > this->capacity())
		{
			size_t len = this->size();
			this->reserve(num);
			for (size_t i = len; i < num; i++)
			{
				this->_start[i] = elmn;
				this->_end++;
			}
		}
	}

七、push_back()尾插函数

    template<typename T>
	void mvector<T>::push_back(T elmn)
	{
		this->reserve(this->size()+1);
		this->_start[this->size()] = elmn;
		this->_end++;
	}

八、pop_back()尾删函数

    template<typename T>
	void mvector<T>::pop_back()
	{
		this->_end -= 1;//尾指针后退一位就行
	}

九、insert()插入函数

插入函数的设计:先开辟对应大小空间,再将pos位置后的数据进行移动,再赋上设定值

    template<typename T>
	void mvector<T>::insert(const_iterator pos, T elmn)
	{
		this->reserve(this->size()+ 1);//检查空间是否足够大
		T* end = this->_end- 1;//指向最后一个元素
		while (end >= pos)
		{
			*(end + 1) = *end;//移位覆盖
			end--;
		}
		*(end+1) = elmn;//插入元素
		this->_end++;
	}
	template<typename T>
	void mvector<T>::insert(iterator pos, size_t count, T elmn)
	{
		size_t len1 = pos - this->_start, len2 = this->size();
		this->reserve(this->size() + count);
		pos = this->_start+len1;//pos地址可能会由于扩容改变,需要重新赋值
		for(size_t i=0;i<count;i++)
		{
			for (size_t j = 0; j < len2; j++)
				this->_end[i-j] = this->_end[i-j-1];//循环移位
			pos[i] = elmn;//给挪出来的空间赋值
		}
		this->_end += count;
	}

十、erase()删除函数

    template<typename T>
	void mvector<T>::erase(iterator pos)
	{
		for (iterator i = pos; i < this->_end - 1; i++)//移位覆盖清除
			*i = *(i + 1);
		this->_end -= 1;
	}
	template<typename T>
	void mvector<T>::erase(iterator begin, iterator end)
	{
		size_t len = end - begin;
		for (iterator i = begin; i < end; i++)
			*i = *(i + len);
		this->_end -= len;
	}

十一、clear()清空函数

    template<typename T>
	void mvector<T>::clear()
	{
		this->erase(this->begin(), this->_end);
	}

十二、at()元素访问函数

    template<typename T>
	T&mvector<T>::at(size_t index)
	{
		return *(this->_start + index);
	}

十三、front(),back()获取头尾元素

    template<typename T>
	T&mvector<T>::front()
	{
		return *this->_start;
	}
	template<typename T>
	T&mvector<T>::back()
	{
		return *(this->_end-1);//返回最后一个元素
	}

十四、swap()交换函数

    template<typename T>
	void mvector<T>::swap(mvector & mvec)
	{
		std::swap(this->_start, mvec._start);//运用库函数交换
		std::swap(this->_end, mvec._end);
		std::swap(this->_endofstorage, mvec._endofstorage);
	}

十五、reserve()预开辟空间函数

template<typename T>
	void mvector<T>::reserve(size_t len)
	{
		if (len >this->capacity())
		{
			size_t sz = this->size();
			T* tmp = new T[len];
			if (this->_start) 
			{
				for (size_t i = 0; i < sz; i++)
					tmp[i] = this->_start[i];
				delete[] _start;
			}
			this->_start = tmp;
			this->_end = tmp + sz;//end指向最后一个元素的下一位
			this->_endofstorage = _start + len;
		}
	}

十六、begin(),end()迭代器

这部分类外写报错,只好写在类中了

        iterator&begin()
		{
			return this->_start;
		}
		iterator&end()
		{
			return this->_end;
		}
		const_iterator&begin()const
		{
			return this->_start;
		}
		const_iterator&end()const
		{
			this->_end;
		}

十七、运算符重载

这部分就重载了【】和赋值=,其他的比较函数还有输入输出流函数也可以重载

    template<typename T>
	mvector<T>&mvector<T>::operator=(const mvector & mvec)
	{
		this->reserve(mvec.capacity());
		for (size_t i = 0; i < mvec.size(); i++)
		{
			this->_start[i] = mvec._start[i];
			this->_end++;
		}
		return *this;
	}


    template<typename T>
	T&mvector<T>::operator[](size_t index)
	{
		return *(this->_start + index);
	}

十八、析构函数

释放_start指向的空间内存

    template<typename T>
	mvector<T>::~mvector()
	{
		if(this->_start)
			delete[]this->_start;
		this->_start = this->_end = this->_endofstorage = NULL;
	}

十九、vector全部模拟实现源码

#include<iostream>
using namespace std;
namespace mxyvector
{
	template<typename T>
	class mvector
	{
		T*_start;
		T*_end;//用指针记录数据元素个数,减去_start即为元素个数
		T*_endofstorage;//记录容量
	public:
		typedef T* iterator;//因使用模板,必须定义在类中
		typedef const T* const_iterator;
		mvector();	//采用模板实现类实现,默认构造函数
		mvector(T*begin, T*end);	//将v[begin(),ens()]区间的元素拷贝给本身
		mvector(size_t n, T elmn);	//构造函数将n个elem拷贝给本身
		mvector(const mvector&mvec);	//拷贝构造函数
		mvector&operator=(const mvector&mvec); //重载=号
		void assign(T* begin, T* end);	//将[begin,end]区间中的数据拷贝复制给本身
		void assign(size_t n, T elmn);	//将n个elem拷贝给本身
		bool empty();	//判断容器是否为空
		size_t capacity()const;	//容器容量
		size_t size()const;	//容器中元素的个数
		void resize(size_t num);	//重新指定容器的长度为num,变长用默认值填充新位置,变短删除超出元素
		void resize(size_t num, T elmn);	//重新指定容器的长度为num,变长用elmn填充新位置,变短删除超出元素
		void push_back(T elmn);	//尾插一个元素
		void pop_back();	//尾删一个元素
		void insert(const_iterator pos, T elmn);	//迭代器指向位置pos插入元素elmn
		void insert(iterator pos, size_t count, T elmn);	//迭代器指向位置pos插入count个元素elmn
		void erase(iterator pos);	//删除迭代器指向的元素
		void erase(iterator begin, iterator end);	//删除迭代器葱begin到end之间的元素
		void clear();	//删除容器中所有元素
		T&at(size_t index);	//返回索引index所指的数据
		T&operator[](size_t index);	//返回索引index所指的数据
		T&front();	//返回容器中的第一个元素
		T&back();	//返回容器中的最后一个数据元素
		void swap(mvector&mvec);	//将mvec与本身的元素互换
		void reserve(size_t len);	//容器预留len个元素长度,预留位置不初始化,元素不可访问
		iterator&begin()
		{
			return this->_start;
		}
		iterator&end()
		{
			return this->_end;
		}
		const_iterator&begin()const
		{
			return this->_start;
		}
		const_iterator&end()const
		{
			this->_end;
		}
		~mvector();	//析构函数
	}; 
	template<typename T>
	mvector<T>::mvector()
	{
		this->_start = this->_end = this->_endofstorage = NULL;
	}
	template<typename T>
	mvector<T>::mvector(T*begin, T*end)
	{
		size_t len = end - begin;//拷贝所需的空间长度
		this->reserve(len);
		for (size_t i = 0; i < len; i++)
		{
			this->_start[i] = begin[i];
			this->_end++;
		}
	}
	template<typename T>
	mvector<T>::mvector(size_t n, T elmn)
	{
		this->reserve(n);
		for (size_t i = 0; i < n; i++)
		{
			this->_start[i] = elmn;
			this->_end++;
		}
	}
	template<typename T>
	mvector<T>::mvector(const mvector & mvec)
	{
		this->reserve(mvec.capacity());
		for (size_t i = 0; i < mvec.size(); i++)
		{
			this->_start[i] = mvec._start[i];
			this->_end++;
		}
	}
	template<typename T>
	mvector<T>&mvector<T>::operator=(const mvector & mvec)
	{
		this->reserve(mvec.capacity());
		for (size_t i = 0; i < mvec.size(); i++)
		{
			this->_start[i] = mvec._start[i];
			this->_end++;
		}
		return *this;
	}
	template<typename T>
	void mvector<T>::assign(T*begin, T* end)
	{
		this->clear();//先清除原有数据
		size_t len = end - begin;
		this->reserve(len);
		for (size_t i = 0; i < len; i++)
		{
			this->_start[i] = begin[i];
			this->_end++;
		}
	}
	template<typename T>
	void mvector<T>::assign(size_t n, T elmn)
	{
		this->clear();
		this->reserve(n);
		for (size_t i = 0; i < n; i++)
		{
			this->_start[i] = elmn;
			this->_end++;
		}
	}
	template<typename T>
	bool mvector<T>::empty()
	{
		return this->_start == this->_end;//如果头尾指针相同,则未存任何元素,为空
	}
	template<typename T>
	size_t mvector<T>::capacity()const
	{
		return this->_endofstorage - this->_start;//地址相减
	}
	template<typename T>
	size_t mvector<T>::size()const
	{
		return this->_end - this->_start;
	}
	template<typename T>
	void mvector<T>::resize(size_t num)
	{
		if (num <= this->size())//指定任意大小空间
		{
			this->_end = this->_start + num;//重新指定尾指针
			this->_endofstorage = this->_start + num;
			return;
		}
		if (num > this->capacity())//扩大开辟空间
			this->reserve(num);
	}
	template<typename T>
	void mvector<T>::resize(size_t num, T elmn)//则个加个初始化赋值
	{
		if (num <= this->size())
		{
			this->_end = this->_start + num;
			this->_endofstorage = this->_start + num;
			return;
		}
		if (num > this->capacity())
		{
			size_t len = this->size();
			this->reserve(num);
			for (size_t i = len; i < num; i++)
			{
				this->_start[i] = elmn;
				this->_end++;
			}
		}
	}
	template<typename T>
	void mvector<T>::push_back(T elmn)
	{
		this->reserve(this->size()+1);
		this->_start[this->size()] = elmn;
		this->_end++;
	}
	template<typename T>
	void mvector<T>::pop_back()
	{
		this->_end -= 1;//尾指针后退一位就行
	}
	template<typename T>
	void mvector<T>::insert(const_iterator pos, T elmn)
	{
		this->reserve(this->size()+ 1);//检查空间是否足够大
		T* end = this->_end- 1;//指向最后一个元素
		while (end >= pos)
		{
			*(end + 1) = *end;//移位覆盖
			end--;
		}
		*(end+1) = elmn;//插入元素
		this->_end++;
	}
	template<typename T>
	void mvector<T>::insert(iterator pos, size_t count, T elmn)
	{
		size_t len1 = pos - this->_start, len2 = this->size();
		this->reserve(this->size() + count);
		pos = this->_start+len1;//pos地址可能会由于扩容改变,需要重新赋值
		for(size_t i=0;i<count;i++)
		{
			for (size_t j = 0; j < len2; j++)
				this->_end[i-j] = this->_end[i-j-1];//循环移位
			pos[i] = elmn;//给挪出来的空间赋值
		}
		this->_end += count;
	}
	template<typename T>
	void mvector<T>::erase(iterator pos)
	{
		for (iterator i = pos; i < this->_end - 1; i++)//移位覆盖清除
			*i = *(i + 1);
		this->_end -= 1;
	}
	template<typename T>
	void mvector<T>::erase(iterator begin, iterator end)
	{
		size_t len = end - begin;
		for (iterator i = begin; i < end; i++)
			*i = *(i + len);
		this->_end -= len;
	}
	template<typename T>
	void mvector<T>::clear()
	{
		this->erase(this->begin(), this->_end);
	}
	template<typename T>
	T&mvector<T>::at(size_t index)
	{
		return *(this->_start + index);
	}
	template<typename T>
	T&mvector<T>::operator[](size_t index)
	{
		return *(this->_start + index);
	}
	template<typename T>
	T&mvector<T>::front()
	{
		return *this->_start;
	}
	template<typename T>
	T&mvector<T>::back()
	{
		return *(this->_end-1);//返回最后一个元素
	}
	template<typename T>
	void mvector<T>::swap(mvector & mvec)
	{
		std::swap(this->_start, mvec._start);//运用库函数交换
		std::swap(this->_end, mvec._end);
		std::swap(this->_endofstorage, mvec._endofstorage);
	}
	template<typename T>
	void mvector<T>::reserve(size_t len)
	{
		if (len >this->capacity())
		{
			size_t sz = this->size();
			T* tmp = new T[len];
			if (this->_start) 
			{
				for (size_t i = 0; i < sz; i++)
					tmp[i] = this->_start[i];
				delete[] _start;
			}
			this->_start = tmp;
			this->_end = tmp + sz;
			this->_endofstorage = _start + len;
		}
	}
	template<typename T>
	mvector<T>::~mvector()
	{
		if(this->_start)
			delete[]this->_start;
		this->_start = this->_end = this->_endofstorage = NULL;
	}
}

二十、main函数测试用例

#include"mvector.hpp"
using namespace mxyvector;
void printMvector(mvector<int>&v)
{
	for (auto i : v)//auto自动判断类型,表示从v中逐一读取
		cout << i << " ";
	cout << endl;
}
void test01()
{
	mvector<int>v1;//默认无参构造
	for (int i = 0; i < 10; i++)
		v1.push_back(i);
	printMvector(v1);
	//通过区间构造
	mvector<int>v2(v1.begin(), v1.end());
	printMvector(v2);
	//n个elmn构造
	mvector<int>v3(7, 3);
	printMvector(v3);
	//拷贝构造
	mvector<int>v4(v3);
	printMvector(v4);
}
void test02()
{
	mvector<int>v1;
	for (int i = 0; i < 10; i++)
		v1.push_back(i);
	printMvector(v1);
	mvector<int>v2;
	v2 = v1;
	printMvector(v2);
	mvector<int>v3;
	v3.assign(v1.begin(), v1.end());
	printMvector(v3);
	mvector<int>v4;
	v4.assign(7, 3);
	printMvector(v4);
}
void test03()
{
	mvector<int>v1;
	for (int i = 0; i < 10; i++)
		v1.push_back(i);
	printMvector(v1);
	if (v1.empty())
		cout << "v1为空" << endl;
	else
	{
		cout << "v1不为空" << endl;
		cout << "v1的容量为:" << v1.capacity() << endl;
		cout << "v1的大小为:" << v1.size() << endl;
	}
	v1.resize(15,3);//指定空间大小
	printMvector(v1);
	v1.resize(5);
	printMvector(v1);
}
void test04()
{
	mvector<int>v1;
	v1.push_back(10);
	v1.push_back(20);
	v1.push_back(30);
	v1.push_back(40);
	v1.push_back(50);
	printMvector(v1);
	v1.pop_back();
	printMvector(v1);
	v1.insert(v1.begin(), 100);
	printMvector(v1);
	v1.insert(v1.begin(), 3, 373);
	printMvector(v1);
	v1.erase(v1.begin());
	printMvector(v1);
	v1.erase(v1.begin() + 1, v1.end());
	printMvector(v1);
	v1.clear();
	printMvector(v1);
}
void test05()
{
	mvector<int>v1;
	for (int i = 0; i < 10; i++)
		v1.push_back(i);
	for (int i = 0; i < v1.size(); i++)
		cout << v1[i] << " ";
	cout << endl;
	for (int i = 0; i < v1.size(); i++)
		cout << v1.at(i) << " ";
	cout << endl;
	cout << "第一个元素为:" << v1.front() << endl;
	cout << "最后一个元素为:" << v1.back() << endl;
}
void test06()
{
	mvector<int>v1;
	for (int i = 0; i < 10; i++)
		v1.push_back(i);
	printMvector(v1);
	mvector<int>v2;
	for (int i = 9; i >=0; i--)
		v2.push_back(i);
	printMvector(v2);
	v1.swap(v2);
	printMvector(v1);
	printMvector(v2);
}
void test07()
{
	mvector<int>v;
	v.reserve(100000);//由实现代码知此时_start仍为空指针
	int num = 0;
	int*p = NULL;
	for (int i = 0; i < 100000; i++)
	{
		v.push_back(i);
		if (p != &v[0])
		{
			p = &v[0];
			num++;
		}
	}
	cout << "num=" << num << endl;
}
int main()
{
	//test01();
	//test02();
	//test03();
	//test04();
	//test05();
	//test06();
	test07();
}

  • 8
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 5
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

...404 Not Found

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值