C++ vector容器详解

vector容器的基本概念

功能:vector容器的功能和数组非常相似,使用时可以把它看成一个数组

vector和普通数组的区别:
1.数组是静态的,长度不可改变,而vector可以动态扩展,增加长度
2.数组内数据通常存储在栈上,而vector中数据存储在堆上

动态扩展:(这个概念很重要)
动态扩展并不是在原空间之后续接新空间,而是找到比原来更大的内存空间,将原数据拷贝到新空间,释放原空间

注意:使用vector之前必须包含头文件 #include<vector>

在这里插入图片描述

1.vector的构造函数

函数原型:
1.vector<T> v ; //使用模板类,默认构造函数
2.vector(v.begin(),v.end()); //将[v.begin(),v.end())区间中的元素拷贝给本身
3.vextor(n,elem); //将n个elem拷贝给本身
4.vector(const vector &v) ; //拷贝构造函数

为了方便测试,我们先定义一个打印输出的函数,利用迭代器实现,这个函数下面会经常使用,迭代器可以理解为指针

void printVector(vector<int>& v)
{
    
    	//利用迭代器打印 v
	for (vector<int>::iterator it = v.begin(); it != v.end(); ++it)
	{
    
    
		cout << *it << " ";
	}
	cout << endl;
}

测试案例:

void text01()
{
    
    
	vector<int> v1;                       //调用1
	for (int i = 0; i < 5; ++i)
	{
    
    
		v1.push_back(i);//向v1末尾添加数据
	}
	vector<int> v2(v1.begin(), v1.end());//调用2
	vector<int> v3(5, 5);                //调用3
	vector<int> v4(v3);                  //调用4
	cout << "打印v2: ";
	printVector(v2);
	cout << "打印v3: ";
	printVector(v3);
	cout << "打印v4: ";
	printVector(v4);
}

测试结果:
在这里插入图片描述

2.vector的赋值操作

函数原型:
1.vector& operator=(const vector &v); //重载赋值运算符
2.assign(v.begin(),v.end()); //将[v.begin(),v.end())区间中的元素赋值给本身
3.assign(n,elem); //将n个elem赋值给本身

测试案例:

void text02()
{
    
    
	vector<int> v1,v2;
	for (int i = 0; i < 5; ++i)
	{
    
    
		v1.push_back(i);
	}
	v2 = v1;                        //调用1,赋值运算符重载
	vector<int> v3,v4;
	v3.assign(v1.begin(), v1.end());//调用2,区间赋值
	v4.assign(5, 9);                //调用3
	cout << "打印v2: ";
	printVector(v2);
	cout << "打印v3: ";
	printVector(v3);
	cout << "打印v4: ";
	printVector(v4);
}

测试结果:
在这里插入图片描述

3.vector的容量与大小

函数原型:
1.empty(); //判断容器是否为空,为空返回1,否则返回0
2.capacity(); //返回容器的容量
3.size(); //返回容器的大小,即容器中元素的个数
4.resize(int num); //重新指定容器的长度为num,若容器变长,则以默认值0填充新位置,如果容器变短,则末尾超过容器长度的元素被删除
5.resize(int num,int elem); //重新指定容器的长度为num,若容器变长,则以elem填充新位置,如果容器变短,则末尾超过容器长度的元素被删除
resize特性:长赋值,短截断

测试案例:

void text03()
{
    
    
	vector<int> v1;
	if (v1.empty())//调用1,如果容器为空,则给其赋值
	{
    
    
		for (int i = 0; i < 5; ++i)
		{
    
    
			v1.push_back(i);
		}
	}
	cout << "打印v1: ";
	printVector(v1);
	cout << "v1的容量为:" << v1.capacity() << endl;//调用2
	cout << "v1的大小为:" << v1.size() << endl;//调用3

	//重新指定容器大小使其变长
	v1.resize(10);       //调用4,增加的长度默认值为0
	cout << "调用4,增加长度后,打印v1: ";
	printVector(v1);
	v1.resize(15, 9);    //调用5,增加的长度赋值为9
	cout << "调用5,增加长度后,打印v1: ";
	printVector(v1);
	//重新指定容器大小使其变短
	v1.resize(10);       //调用4,删除了上一步中最后赋值为9的5个长度
	cout << "调用4,减小长度后,打印v1: ";
	printVector(v1);
	v1.resize(5, 9);     //调用5,删除了上一步中默认值为0的5个长度
	cout << "调用5,减小长度后,打印v1: ";
	printVector(v1);
}

测试结果:
在这里插入图片描述

4.vector的插入和删除

函数原型:
1.push_back(ele); //尾部插入元素ele
2.pop_back(); //删除最后一个元素
3.insert(const_iterator pos,ele); //在迭代器指向的位置pos处插入一个元素ele
4.insert(const_iterator pos,int count,ele); //在迭代器指向的位置pos处插入count个元素ele
5.erase(const_iterator pos); //删除迭代器指向的元素
6.erase(const_iterator begin,const_iterator end); //删除迭代器从begin到end之间的元素
7.clear(); //删除容器中所有元素

测试案例:

void text04()
{
    
    
	vector<int> v1;
	for (int i = 0; i < 5; ++i)
	{
    
    
		v1.push_back(6);//调用1,尾部插入元素6
	}
	cout << "打印v1: ";
	printVector(v1);
	v1.pop_back();//调用2,删除最后一个元素
	cout << "调用2,删除最后一个元素后,打印v1: ";
	printVector(v1);
	v1.insert(v1.begin(),20);//调用3,在首位插入20
	cout << "调用3,在首位插入20,打印v1: ";
	printVector(v1);
	v1.insert(v1.end(), 3, 20);//调用4,在尾部插入3个20
	cout << "调用4,在尾部插入3个20,打印v1: ";
	printVector(v1);
	v1.erase(v1.begin()); //调用5,在首位删除一个元素
	cout << "调用5,在首位删除一个元素,打印v1: ";
	printVector(v1);
	v1.erase(v1.begin(),v1.end()); //调用6,删除首位到末尾所有元素,也就是删除全部元素
	cout << "调用6,删除首位到末尾所有元素,打印v1: ";
	printVector(v1);
	v1.clear();//调用7,清空所有元素
}

测试结果:
在这里插入图片描述

5.vector数据存取

函数原型:
1.at(int idx); //返回索引idx所指的数据
2.operator[]; //返回[]内索引所指的数据
3.front(); //返回容器中第一个元素
4.back(); //返回容器中最后一个元素

测试案例:

void text05()
{
    
    
	vector<int> v;
	for (int i = 0; i < 5; ++i)
	{
    
    
		v.push_back(i);
	}
	//利用at访问v
	cout << "调用1,打印v: ";
	for (int i = 0; i < v.size(); ++i)
	{
    
    
		cout << v.at(i) << " ";//调用1
	}
	cout << endl;
	//利用[]访问v
	cout << "调用2,打印v: ";
	for (int i = 0; i < v.size(); ++i)
	{
    
    
		cout << v[i] << " ";//调用2
	}
	cout << endl;
	cout << "容器中第一个元素是:" << v.front() << endl;//调用3
	cout << "容器中最后一个元素是:" << v.back() << endl;//调用4
}

测试结果:
在这里插入图片描述

6.vector互换容器

函数原型:
swap(v); //容器v和当前容器互换

测试案例1:基本使用

void text06_1()
{
    
    
	vector<int> v1,v2;
	for (int i = 0; i < 10; ++i)
	{
    
    
		v1.push_back(i);
		v2.push_back(9 - i);
	}
	cout << "交换前:" << endl;
	printVector(v1);
	printVector(v2);
	cout << "交换后:" << endl;
	v1.swap(v2);   //调用互换函数
	printVector(v1);
	printVector(v2);
}

测试结果:
在这里插入图片描述

测试案例2:实际用途

void text06_2()
{
    
    
	vector<int> v;
	for (int i = 0; i < 1000; ++i)
	{
    
    
		v.push_back(i);
	}
	cout << "初始时:" << endl;
	cout << "v的容量:" << v.capacity() << endl;
	cout << "v的大小:" << v.size() << endl;
	
	cout << "重新指定空间后:" << endl;
	v.resize(10);
	cout << "v的容量:" << v.capacity() << endl;
	cout << "v的大小:" << v.size() << endl;

	//巧用swap收缩内存
	cout << "swap收缩内存后:" << endl;
	vector<int>(v).swap(v);   //vector<int>(v) 是创建一个匿名对象,并拷贝v的数据
	                          //以此匿名对象与v交换,交换完后系统自动删除匿名对象
	cout << "v的容量:" << v.capacity() << endl;
	cout << "v的大小:" << v.size() << endl;
}

测试结果:
在这里插入图片描述

7.vector预留空间

功能:减少vector在动态扩容时的扩展次数
每次使用push_back(v)时,如果容器v的大小要超过v的容量时,系统就会对v进行一次动态扩容,至于扩大多少空间,由系统决定

函数原型:
reserve(int len);//容器预留len个元素长度,也就是把容量扩为len,
预留的位置并不初始化,同时也不可访问

测试案例:

void text07()
{
    
    
	vector<int> v1,v2;
	v2.reserve(10000);//给v2设置预留空间,v1不设置

	//对比v1,v2,系统需要动态扩容多少次
	int num1 = 0;       //扩容次数
	int num2 = 0;       
	int capacity1 = 0;  //容量大小
	int capacity2 = 0;
	for (int i = 0; i < 10000; ++i)
	{
    
    
		v1.push_back(i);
		if (capacity1 != v1.capacity())//计算扩容次数,当容量不相等时,证明系统扩容了
		{
    
    
			capacity1 = v1.capacity();
			++num1;
		}

		v2.push_back(i);
		if (capacity2 != v2.capacity())
		{
    
    
			capacity2 = v2.capacity();
			++num2;
		}
	}
	cout << "系统对v1扩容" << num1 << "次" << endl;
	cout << "系统对v2扩容" << num2 << "次" << endl;
}

测试结果:
在这里插入图片描述

写在最后

vector容器算是C++中最常用的容器之一了,我在真正学习它之前就经常用了,看多了别人怎么用,自己也就大概会一点了,但是那时候不知道它的具体原理,现在学习完了,详细总结了vector的具体用法供大家一起学习,喜欢的话,点赞收藏加关注喽!

猜你喜欢

转载自blog.csdn.net/qq_52324409/article/details/121000029