C++—vector的使用

一、vector的介绍

说的简单点:
vector是可以动态增长的数组容器

  1. vector是表示可变大小数组的序列容器。
  2. 就像数组一样,vector也采用的连续存储空间来存储元素。也就是意味着可以采用下标对vector的元素进行访问,和数组一样高效。
  3. 本质讲,vector使用动态分配数组来存储它的元素。当新元素插入时候,这个数组需要被重新分配大小为了增加存储空间。
  4. vector分配空间策略:vector会分配一些额外的空间以适应可能的增长,因为存储空间比实际需要的存储空间更大。。
  5. 因此,vector占用了更多的存储空间,为了获得管理存储空间的能力,并且以一种有效的方式动态增长。
  6. 与其它动态序列容器相比(deques, lists and forward_lists), vector在访问元素的时候更加高效,在末尾添加和删除元素相对高效。对于其它不在末尾的删除和插入操作,效率更低。比起listsforward_lists统一的迭代器和引用更好。

如果想要了解更多请猛戳这里

二、vector的使用

2.1vector构造函数

构造函数 功能
vector() 无参构造
vector(size_type n, const value_type& val = value_type()) 构造并初始化n个val
vector (const vector& x)重点 拷贝构造
vector (InputIterator fifirst, InputIterator last) 使用迭代器进行初始化构造
void test1()
{
    
    
	vector<int> v1;//无参的构造用的最多
	vector<int> v2(10,1);//用10个1来初始化
	vector<int> v3(v2.begin(),v2.end());//用一段迭代器区间去初始化
	vector<int> v4(v3);//拷贝构造

	string s("hello");
	vector<char> v5(s.begin(), s.end());//不同STL的迭代器区间也可以初始化
}

结果展示:
打开监视窗口观察,确实初始化好了
在这里插入图片描述
问题
对于下面这种情况:

string s; 和 vector<char> v; 

是不是差不多呢?能不能相互替代呢?

 不行的!因为string末尾带着\0,而且string提供了一些专门的字符串相关的接口函数,比如:operator+=,c_str,find等等函数

2.2迭代器的使用

iterator的使用 功能
begin+end 获取第一个数据位置的iterator/const_iterator, 获取最后一个数据的下一个位置的iterator/const_iterator
rebegin+rend 获取最后一个数据位置的reverse_iterator,获取第一个数据前一个位置reverse_iterator

在这里插入图片描述

//vector中如何遍历
void test2()
{
    
    
	vector<int> v;
	v.push_back(1);
	v.push_back(2);
	v.push_back(3);
	v.push_back(4);

	//下标[]遍历
	for (size_t i = 0; i < v.size(); ++i)
	{
    
    
		v[i] += 1;
		cout << v[i] << " ";
	}
	cout << endl;

	//迭代器
	vector<int>::iterator it=v.begin();
	while (it != v.end())
	{
    
    
		
		cout << *it << " ";
		++it;
	}
	cout << endl;
	
	//反向迭代器
   	vector<int>::reverse_iterator rit = v.rbegin();
	while (rit != v.rend())
	{
    
    
		cout << *rit << " ";
		++rit;
	}
	//范围for
	for (auto e : v)
	{
    
    
		cout << e << " ";
	}
	cout << endl;
}

2.3空间增长问题

容量函数 功能
size( ) 获取数据个数
capacity( ) 获取容量大小
empty( ) 判空
resize( ) 改变size
reserve( ) 改变capacity
void test3()
{
    
    
	vector<int> v;
	v.push_back(1);
	v.push_back(2);
	v.push_back(3);
	v.push_back(4);

	cout << v.size() << endl;
	cout << v.capacity() << endl;
	cout << v.empty() << endl;
	cout << endl;

	v.reserve(100);//改变capacity
	cout << v.size() << endl;
	cout << v.capacity() << endl;
	cout << v.empty() << endl;
	cout << endl;

	v.resize(10,1);//改变size,默认给上缺省值0,它可以 扩容+初始化 或者 删除数据
	cout << v.size() << endl;
	cout << v.capacity() << endl;
	cout << v.empty() << endl;
	cout << endl;

	v.resize(2);
	cout << v.size() << endl;
	cout << v.capacity() << endl;
	cout << v.empty() << endl;
	cout << endl;
}

结果展示:
在这里插入图片描述
总结

  • capacity的代码在vs和g++下分别运行会发现,vs下capacity是按1.5倍增长的,g++是按2倍增长的。这个问题经常会考察,不要固化的认为,顺序表增容都是2倍,具体增长多少是根据具体的需求定义的。vs是PJ版本STL,g++是SGI版本STL。
  • reserve只负责开辟空间,如果确定知道需要用多少空间,reserve可以缓解vector增容的代价缺陷问题。
  • resize在开空间的同时还会进行初始化,影响size。

2.4增删查改问题

函数 功能
push_back( ) 尾插
pop_back( ) 尾删
insert( ) 在pos之前插入
erase( ) 删除
swap( ) 交换两个vector的数据空间
operator[ ]常用 下标位置访问
find( ) 这个是算法库里面实现的查找(algorithm),不是vector的成员函数
void test4()
{
    
    
	vector<int> v;
	//push_back尾插
	v.push_back(1);
	v.push_back(2);
	v.push_back(3);
	v.push_back(4);
	
	//find查找
	vector<int>::iterator ret = find(v.begin(), v.end(),3);
	auto ret1 = find(v.begin(), v.end(), 3);
	//可以用auto替换
	if (ret != v.end())
	{
    
    
		cout << "找到了" << endl;
	}
	v.insert(ret, 100);
	for (auto e : v)
	{
    
    
		cout << e << " ";
	}

	vector<int>::iterator pos = find(v.begin(), v.end(), 1);
	if (pos != v.end())//判断数据是否合法
	{
    
    
		//erase删除
		v.erase(pos);
	}
	cout << endl;
}

结果演示:
在这里插入图片描述
operator[ ] 和范围for是vector中常用的遍历手段

// vector使用这两种遍历方式是比较便捷的。
#include <iostream>
#include <vector>
using namespace std;
int main()
{
    
    
	int a[] = {
    
     1, 2, 3, 4 };
	vector<int> v(a, a + sizeof(a) / sizeof(int));

	// 通过[]读写第0个位置。
	v[0] = 10;
	cout << v[0] << endl;

	// 通过[i]的方式遍历vector
	for (size_t i = 0; i < v.size(); ++i)
		cout << v[i] << " ";
	cout << endl;

	vector<int> swapv;
	swapv.swap(v);
	cout << "v data:";
	for (size_t i = 0; i < v.size(); ++i)
		cout << v[i] << " ";
	cout << endl;

	cout << "swapv data:";
	for (size_t i = 0; i < swapv.size(); ++i)
		cout << swapv[i] << " ";
	cout << endl;

	// C++11支持的新式范围for遍历
	for (auto x : v)
		cout << x << " ";
	cout << endl;
	return 0;
}

说明:vector是支持迭代器的,还可以用范围for对vector进行遍历,支持迭代器就支持范围for,因为在编译时编译器会自动将范围for替换为迭代器遍历的形式。

猜你喜欢

转载自blog.csdn.net/weixin_57675461/article/details/123960637