【C++】动态数组vector的使用
vector的方法
std::vector 是 C++ 标准库中最常用的动态数组容器,提供了丰富的成员方法来管理元素和内存。以下按功能分类列出核心常用方法,方便快速查阅:
一、基础属性与状态查询
size()
:返回当前容器中元素的个数(无符号类型 size_t)。empty()
:判断容器是否为空(为空返回 true,否则 false,效率比 size() == 0 更高)。capacity()
:返回容器当前已分配的内存可容纳的元素个数(大于等于 size(),体现 “预分配内存” 特性)。max_size()
:返回容器理论上可容纳的最大元素个数(受系统内存限制,通常无需关注)。
二、元素访问
operator[](size_t pos)
:通过下标访问指定位置(pos)的元素,不检查下标合法性(越界会导致未定义行为)。at(size_t pos)
:通过下标访问元素,会检查下标合法性(越界时抛出 out_of_range 异常,更安全)。front()
:返回容器中第一个元素的引用(容器非空时使用,否则未定义)。back()
:返回容器中最后一个元素的引用(容器非空时使用,否则未定义)。data()
:返回指向容器底层数组首元素的指针(可用于兼容 C 风格数组操作)。
三、元素修改(增删改)
- 添加元素
push_back(const T& val)
:在容器末尾添加一个元素(val 的拷贝),内存不足时会自动扩容。emplace_back(Args&&... args)
:在容器末尾直接构造一个元素(无需先创建临时对象,效率比 push_back 高,C++11 及以后支持)。insert(iterator pos, const T& val)
:在迭代器 pos 指向的位置插入一个元素(val 的拷贝),插入后原迭代器可能失效(需重新获取)。
- 删除元素
pop_back()
:删除容器最后一个元素(不返回该元素,容器非空时使用,否则未定义)。erase(iterator pos)
:删除迭代器 pos 指向的单个元素,返回指向删除位置下一个元素的迭代器(原迭代器失效)。erase(iterator first, iterator last)
:删除 [first, last) 区间内的所有元素,返回指向区间末尾下一个元素的迭代器。clear()
:删除容器中所有元素(size() 变为 0,但 capacity() 不变,内存未释放)。
- 其他修改
assign(iterator first, iterator last)
:用 [first, last) 区间的元素替换容器中所有现有元素(会清空原元素)。assign(size_t n, const T& val)
:用 n 个值为 val 的元素替换容器中所有现有元素。
四、内存管理
reserve(size_t new_cap)
:预分配内存,使容器的 capacity() 至少为 new_cap(仅当 new_cap > 当前 capacity() 时生效,用于减少扩容次数,提升效率)。shrink_to_fit()
:将容器的 capacity() 缩减至与 size() 一致(释放多余内存,C++11 及以后支持,仅为 “建议”,编译器可能不执行)。resize(size_t new_size)
:调整容器的 size() 为 new_size:- 若
new_size > 当前 size()
:新增元素默认初始化(内置类型为 0,类类型调用默认构造)。 - 若
new_size < 当前 size()
:删除末尾多余元素。
- 若
五、迭代器(遍历与定位)
begin() / end():
begin()
:返回指向容器第一个元素的迭代器(可读可写,非 const 容器用)。end()
:返回指向容器末尾(最后一个元素的下一个位置) 的迭代器(不可访问元素,仅用于标记范围)。cbegin() / cend()
:返回只读迭代器(const 迭代器,即使容器非 const,也只能读元素,不能修改)。rbegin() / rend()
:返回反向迭代器(从容器末尾向开头遍历,rbegin() 指向最后一个元素,rend() 指向第一个元素的前一个位置)。
六、容器操作
swap(vector& other)
:交换当前容器与 other 的所有元素和内存(效率极高,仅交换底层指针,不拷贝元素)。emplace(iterator pos, Args&&... args)
:在迭代器 pos 指向的位置直接构造一个元素(类似 emplace_back,但支持指定位置,C++11 及以后)。
示例代码
#include<bits/stdc++.h>using namespace std;int main() {// vector的使用vector<int> vec;vec.push_back(10); // 末尾添加10vec.push_back(20); // 末尾添加10cout << "vec.size=" << vec.size() << endl;cout << "vec.at(1)=" << vec.at(1) << endl;vec.insert(vec.begin(), 5); // 开头插入5vec.pop_back(); // 删除末尾for(int i = 0; i < vec.size(); i++) {cout << vec[i] << " ";}return 0;
}
运行结果:
在vector里使用struct
#include<bits/stdc++.h>
using namespace std;struct Person {string name;int age;Person(string name, int age): name(name), age(age) {}void print() {cout << "Name: " << name << "Age: " << age << endl;}
};int main() {// vector的使用 - intvector<int> vec;vec.push_back(10); // 末尾添加10vec.push_back(20); // 末尾添加10cout << "vec.size=" << vec.size() << endl;cout << "vec.at(1)=" << vec.at(1) << endl;vec.insert(vec.begin(), 5); // 开头插入5vec.pop_back(); // 删除末尾for(int i = 0; i < vec.size(); i++) {cout << vec[i] << " ";}cout << endl;cout << "----------------------------" << endl;// vector的使用 - structvector<Person> people;people.push_back(Person("小猫咪", 25));for (auto & p : people) { // const& 避免拷贝,提高效率p.print(); // 直接访问每个 Person 对象}// 查找姓名为 "大老虎" 的人string targetName = "大老虎";bool isfind = false;for(int i = 0; i < people.size(); i++) {Person p = people[i];if(p.name == targetName) {cout << "Finded! ";p.print();isfind = true;break;}}if(!isfind) {cout << targetName << "Not Found!" << endl;}// 添加大老虎people.push_back(Person("大老虎", 45));// 删除第一位的人people.erase(people.begin() + 0);for(auto it = people.begin(); it != people.end(); ++it) {it->print();}cout << "----------------------------" << endl;return 0;
}
运行结果:
这段代码里我使用了3种方式打印vector里的内容,读者可以选择自己喜欢的方式去尝试~