C++ vector常用方法_C++ vector容器高频使用函数汇总

size() 返回当前元素个数,capacity() 返回已分配内存可容纳的元素总数;resize(n) 改变 size() 并可能初始化新元素,reserve(n) 仅预分配 capacity() 不改变 size()。

vector 的 size() 和 capacity() 到底有什么区别?

很多人调用 size() 看到 10 就以为内存占了 10 个元素的空间,其实不一定。size() 返回当前实际存了多少个元素,capacity() 才是底层分配的连续内存能容纳多少个——它往往 ≥ size(),因为 vector 会预留空间避免频繁 realloc。

  • 插入大量数据前,用 reserve(n) 预分配容量,可避免多次拷贝重分配(尤其对非 trivial 类型)
  • resize(n) 会改变 size():若 n > size(),末尾补默认构造对象;若 n ,直接截断(已析构)
  • shrink_to_fit() 是非强制请求,编译器可能忽略;想真正释放多余内存,得靠 swap 技巧:
    std::vector(v).swap(v);

用 at() 还是 [] 访问元素?什么时候会抛异常?

operator[] 不做边界检查,越界是未定义行为(常见 crash 或静默脏读);at(index) 会检查,越界时抛 std::out_of_range 异常。

  • 调试阶段建议优先用 at(),上线后若确定索引安全、且性能敏感,再换 []
  • 迭代器失效场景下(如 push_back() 触发扩容),所有已有迭代器、指针、data() 返回的地址都失效,但 at()[] 只依赖 index,不受影响
  • 注意:空 vector 调用 front()back() 同样是未定义行为,必须先判空

erase() 删除元素为什么容易出错?怎么安全批量删?

erase(iterator) 返回下一个有效迭代器,不是 void;如果写成 v.erase(it++); 就跳过下一个元素——因为 it++ 先返回旧值再自增,而 erase 已让旧 it 失效。

  • 单删推荐写法:
    it = v.erase(it); // 安全,it 指向原 it+1
  • 删满足条件的多个元素,用 remove-erase 惯用法:
    v.erase(std::remove_if(v.begin(), v.end(), [](int x) { return x % 2 == 0; }), v.end());
  • 不要在循环中用 for (int i = 0; i 边删边改 size,会导致漏删或越界;改用反向遍历或 while + erase 返回值

vector 是特化,别把它当普通容器用

std::vector 是 C++ 标准强制要求的位压缩特化,它不存储 bool 对象,而是把 8 个 bool 打包进 1 字节。这导致几个关键差异:

  • operator[] 返回的是代理对象 std::vector::reference,不是 bool&,所以不能取地址:
    bool* p = &v[0]; // 编译失败
  • 迭代器不是原生指针,std::vector::iterator 是自定义类,某些算法(如需要指针算术的)可能不兼容
  • 若需布尔数组且要支持取址、稳定迭代器,改用 std::dequestd::vector(用 0/1 代替 false/true)

vector 的“常用”背后藏着不少隐式契约:capacity 变化时机、迭代器失效规则、特化陷阱……这些不显眼的地方,才是线上 bug 最爱藏身的位置。