vector与set区别(基础知识)

本文对比了C++中vector和set两种容器的特点。vector允许重复元素并保持元素的插入顺序,而set则确保所有元素唯一且不重复,自动排序,并且对某些操作符未进行重载。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

首先,vector是序列式容器而set是关联式容器。set包含0个或多个不重复不排序的元素。也就是说set能够保证它里面所有的元素都是不重复的。另外对set容器进行插入时可以指定插入位置或者不指定插入位置。如insert(v.begin(),1),也可以直接用insert(1)。还有一点是

set对一些操作符没有进行重载,如<

下面是举个例子:

 

 

[cpp]  view plain copy
  1. #include <iostream>  
  2. #include <list>  
  3. #include <vector>  
  4. #include <deque>  
  5. #include <set>  
  6. using namespace std;  
  7. int main(void)  
  8. {  
  9.     vector<int> v;  
  10.     v.insert(v.begin(),1);  //如果使用insert(1)不指定插入位置,会出错  
  11.     v.insert(v.begin(),2);  
  12.     v.insert(v.begin(),1);  
  13.     v.insert(v.begin(),3);  
  14.     vector<int>::iterator vp = v.begin();  
  15.     for(vp = v.begin();vp < v.end(); vp++)  
  16.         cout << *vp << endl;  
  17.     return 0;  
  18. }   
  19.   
  20. 运行程序输出的结果是:  
  21. 3  
  22. 1  
  23. 2  
  24. 1  

 

 

 

[cpp]  view plain copy
  1. #include <iostream>  
  2. #include <list>  
  3. #include <vector>  
  4. #include <deque>  
  5. #include <set>  
  6. using namespace std;  
  7. int main(void)  
  8. {  
  9.     set<int> v;  
  10.     v.insert(v.begin(),1);  
  11.     v.insert(v.begin(),2);  
  12.     v.insert(v.begin(),1);  
  13.     v.insert(v.begin(),3);  
  14.     set<int>::iterator vp = v.begin();  
  15.     //for(vp = v.begin();vp < v.end(); vp++)  //如果使用这句会出错,因为set容器对<没有重载  
  16.     while(vp!=v.end())  
  17.         cout << *vp++ << endl;  
  18.     return 0;  
  19. }  
  20.   
  21. 运行后结果是:  
  22. 1  
  23. 2  
  24. 3  
  25. 也就是说,set容器对有重复的元素只取其中的一个。 

 

<think>好的,用户现在问的是C++标准库中的vectorset区别。之前他们问过pair和map,现在可能是在继续学习容器相关的知识。我需要先回顾一下vectorset的基本概念,然后找出它们的核心区别。 首先,vector是动态数组,支持随机访问,元素按插入顺序存储,允许重复。而set是关联容器,基于红黑树实现,元素自动排序且唯一。用户可能想知道什么时候用哪个,以及它们的性能差异。 接下来,我需要考虑用户的使用场景。他们可能是刚开始学习C++,或者是需要在实际项目中选择合适的容器。比如,如果用户需要快速查找,可能会考虑set的O(log n)查找时间,而如果需要高效的随机访问,vector的O(1)访问更合适。 用户的真实需求可能不仅仅是了解区别,而是如何在实际中应用。比如,处理大量数据时,插入和删除操作的效率差异。或者是否需要维护元素的唯一性。另外,可能需要注意内存使用情况,vector是连续存储,可能预分配空间,而set每个节点单独分配,可能有更多开销。 需要详细说明两者的内部结构,比如vector的动态数组和倍增扩容机制,而set的红黑树结构。还要比较它们的操作复杂度,比如插入、删除、查找的时间复杂度,以及迭代器稳定性的问题。 可能用户还会混淆其他容器,比如list或者unordered_set,但当前问题只涉及vectorset,所以保持专注。需要给出典型的使用场景,例如vector适用于需要频繁访问而少插入删除的情况,set适用于需要自动排序和唯一性的情况。 最后,提供代码示例帮助理解,比如vector的push_back和索引访问,set的insert和遍历。总结时要强调主要区别:存储方式、元素唯一性、性能特点,以及适用场景。确保回答结构清晰,对比明确,帮助用户做出正确选择。</think>在C++标准库中,`std::vector`和`std::set`是两种常用但用途截然不同的容器,核心区别如下: --- ### **1. 基础定义** - **`std::vector`** 是**动态数组**,支持快速随机访问,元素按插入顺序存储,允许重复值。例如: $$std::vector<int> vec = \{3, 1, 4, 1, 5\};$$ 通过索引(如`vec[2]`)直接访问元素。 - **`std::set`** 是**关联容器**,基于红黑树实现,元素**自动排序**且**唯一**。例如: $$std::set<int> s = \{3, 1, 4, 1, 5\};$$ 实际存储为$\{1, 3, 4, 5\}$(去重并按升序排列)。 --- ### **2. 核心区别** | **特性** | `std::vector` | `std::set` | |------------------|----------------------------------------|-----------------------------------------| | **数据组织** | 连续内存,动态数组 | 红黑树(平衡二叉搜索树) | | **元素顺序** | 按插入顺序存储 | 自动按升序(或自定义排序规则)排列 | | **唯一性** | 允许重复元素 | 元素唯一(插入重复值时自动忽略) | | **访问方式** | 随机访问(通过索引,$O(1)$) | 只能通过迭代器遍历或查找($O(\log n)$) | | **插入/删除** | 尾部插入高效(均摊$O(1)$),中间操作需移动元素($O(n)$) | 插入/删除保证$O(\log n)$复杂度 | | **内存占用** | 连续内存(可能预分配空间) | 分散内存(树节点独立分配) | | **头文件** | `<vector>` | `<set>` | --- ### **3. 典型使用场景** - **`std::vector`** - 需要频繁随机访问元素(如数组操作)。 - 元素顺序重要且可能重复(如日志记录)。 - 需要缓存友好性(连续内存加速遍历)。 - **`std::set`** - 需要自动排序和唯一性(如维护一组唯一ID)。 - 频繁插入/删除且需保证性能(如实时更新的排行榜)。 - 需要快速查找元素是否存在(`s.find(x)`效率高于遍历`vector`)。 --- ### **4. 代码示例** ```cpp // vector 示例:动态数组操作 std::vector<int> vec = {5, 2, 2, 8}; // 允许重复 vec.push_back(3); // 尾部插入(高效) std::cout << vec[3]; // 输出 8(随机访问) // set 示例:唯一且有序 std::set<int> s = {5, 2, 2, 8}; // 实际存储 {2, 5, 8} s.insert(3); // 插入新元素,自动排序 if (s.find(5) != s.end()) { // 查找复杂度 O(log n) std::cout << "5 exists in set"; } ``` --- ### **5. 关键总结** - **存储方式**:`vector`是连续内存的动态数组,`set`是树状结构的关联容器。 - **唯一性**:`vector`允许重复,`set`强制唯一。 - **性能差异**: - `vector`适合随机访问和尾部操作,中间插入/删除效率低。 - `set`适合需要自动排序、唯一性和稳定性能的场景。 根据需求选择: - 需要**顺序访问**或**缓存效率** → **`vector`** - 需要**快速查找**或**动态维护有序唯一数据** → **`set`**
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值