STL中常用数据结构及用法

C++中的STL(Standard Template Library),即标准模板库,中包含了很多编程时常用的数据结构,省去了自己临时写的麻烦,这里就来总结一下。如果有错误或写的不好的地方还请多指正。

首先稍微介绍下iterator(迭代器),iterator不是数据结构,所有容器都提供获得迭代器的元素,声明时,其数据类型必须与容器的数据类型一致。其作用主要是用来遍历和删除元素。

操作 效果
begin() 返回一个迭代器,指向第一个元素
end() 返回一个迭代器,指向最后一个元素之后

左闭右开

文章目录

  • vector
  • map
  • set
  • stack
  • queue
  • priority_queue

vector

#include < vector > 向量,不定长数组。
与数组的区别在于声明时不需要指定长度,vector动态分配空间(线性连续地址)。插入和删除都比数组要方便很多。vector可以直接赋值,还可以作为函数的参数或者返回值,而无须像传递数组那样用另一个变量指定元素个数。

  • 创建vector对象:
    //默认初始化,v1为空vector<int> v1;     //初始10个值为0的元素vector<int> v2(10);  //初始10个值为8.6的元素vector<double> v3(10,8.6)   
  • 访问:
 //直接通过下标就能访问v2[2]=3;cout<<v2[2]<<endl;//通过迭代器访问cout<<*(v2.begin()+2)<<endl
  • 遍历
    //①通过下标遍历for(int i=0;i<v3.size();i++)cout<<v3[i]<<' ';//②通过迭代器遍历(推荐)vector<int>::iterator it;for(it=v2.begin();it!=v2.end();it++){cout<<*it<<' ';}
  • 插入元素
   // ①元素尾部扩张v.push_back(9);// ②指定位置插入v.insert(v.begin()+2,1);v.insert(v.end(),3);
  • 删除元素
 //删除单个元素v.erase(v.begin()+1);//删除区间内所有元素v.erase(v.begin()+2,v.begin()+5);//清空v.clear();
  • 查找元素
    需要查操作的话一般不使用vector,而是set或multiset。
    方法:在vector中查找元素及其位置

  • 排序

 //递增sort(v.begin(),v.end());//递减sort(v.begin(),v.end(),greater<int>());//自定义结构体排序struct Node{int a;int b;};bool cmp(Node x,Node y){return x.a<y.a;}vector<Node> v;sort(v.begin(),v.end(),cmp);
  • 其他
    //元素反向排列reverse(v.begin(),v.end());//获取向量大小(元素个数)v.size()//向量是否为空v.empty()
  • 例题:HDU 4841:圆桌问题(vector应用)

map

#include< map > 映射,键值对容器。

map就是从键(key)到值(value)的映射。因为重载了 [ ] 运算符,map更像是数组的“高级版”。例如可以用一个map< string,int>month_name来表示“月份名字到月份编号”的映射,然后用 month_name[“July”]=7 这样的方式来赋值。

类似于Python中的字典Dictionary与Java中的TreeMap。
所有元素会根据key值排序(默认升序,如果键值为字符串就是字典序),map中的所有元素都是pair,同时拥有实值和键值,pair的first为键值second为实值,底层将它的first作为红黑树的排序key。
map不允许有两个相同键值的元素。map的迭代器不能修改键值,但可以修改实值。主要用于处理带有键值的记录性元素数据的快速插入、删除和检索。

  • 创建map对象
 map<string,double> m;
  • 插入和访问
    (访问时如果map中不存在该键值,实值为空,对于数字则为0,字符串则为空串。)
    m["Jack"]=98.5;cout<<m["Jack"]<<endl;
  • 遍历
    map<string,double>::iterator it;for(it=m.begin();it!=m.end();it++)cout<<(*it).first<<":"<<(*it).second<<endl;
  • 删除
    //通过键值删除m.erase("Jack");//清空m.clear();

还有一种方法是遍历删除,既可以通过键值,也可以通过实值,不过由于迭代器的属性,这种方法不注意的话很容易出错。这里贴两个大神的链接:
c++ 关于map的遍历 删除
c++如何遍历删除map/vector里面的元素

  • 查找
    使用键值进行查找操作。大多数情况直接用键值访问就行了,很少用到下面的m.find()

Searches the container for an element with a key equivalent to k and returns an iterator to if found,otherwise it returns an iterator to map::end

1.用find函数来定位键值出现位置,它返回的一个迭代器,当键值出现时,它返回所在位置的迭代器,如果map中没有要查找的键值,它返回的迭代器等于end函数返回的迭代器

    map<string,double>::iterator it;it=m.find("Jack");cout<<(*it).first<<":"<<(*it).second<<endl;//等价于cout<<"Jack"<<":"<<m["Jack"]<<endl;

2.用count函数来判定键值是否出现,count函数的返回值只有两个,键值出现返回1,否则返回0

    if(m.count("Jack"))cout<<"FOUND"<<endl;elsecout<<"NOT FOUND"<<endl;//等价于if(m["Jack"])cout<<"FOUND"<<endl;elsecout<<"NOT FOUND"<<endl;
  • 例题: POJ 1008:Maya Calendar (模拟)

set

#include< set > 集合

Sets are containers that store unique elements following a specific order.

类似于Java中的TreeSet,set就是数学上的集合——每个元素最多出现一次,其中的元素自动排序,自定义类型构造set时,必须定义"小于"运算符。一个集合通过一个链表来组织,在插入操作和删除操作上比向量(vector)快,但查找或添加末尾的元素时会有些慢。具体实现采用了红黑树的平衡二叉树的数据结构。

  • 创建set对象
set<int> s1;    //默认升序//-----------------//struct comp
{bool operator() ( const int& lhs,  const int& rhs ){return lhs > rhs ;}
};
set<int, comp> s2;   //降序//--------------//struct Node
{int x;int y;friend bool operator < (Node a, Node b)//结构体排序(重载<操作符):{return a.x<b.x; //按照x升序}
};set<Node> s3;
  • 插入和访问
    **set不支持随机访问!*因此(s.begin+1)这种操作都是非法的,只能通过迭代器移动来访问
    s1.insert(5);s2.insert(Node{8,5});cout<<*s1.begin()<<endl;//第一个元素cout<<*(--s1.end())<<endl;//最后一个元素
  • 遍历
 //只能通过迭代器遍历set<int>::iterator it;for(it=s1.begin();it!=s1.end();it++)cout<<*it<<endl;
  • 删除
    //删除值为5的元素,返回删除的元素个数s1.erase(5);   //删除首个元素,无返回值s1.erase(s1.begin());   //清空s1.clear();
  • 查找
 if(s1.find(5)!=s1.end())cout<<"FOUND"<<endl;elsecout<<"NOT FOUND"<<endl;

查找操作对应find函数,如果存在该元素,返回指向该元素的迭代器,否则返回end。
值得一提的是对自定义结构体的查找操作则比较复杂: C++ STL set::find的用法

stack

#include < stack >,堆栈

这个就是咱们数据结构中学的栈,栈的操作只有几种方法

  • 声明
 stack<int> s;
  • 入栈
 s.push(8);
  • 出栈
 s.pop();
  • 取栈顶元素(但不删除)
 s.top();

例题:HDU 1022:Train Problem I(堆栈的基本应用)

queue

priority_queue

总结——STL 常用数据结构及用法相关推荐

  1. STL 常用容器的底层数据结构

    STL 常用容器的底层数据结构实现 1.vector 底层数据结构为数组 ,支持快速随机访问 2.list 底层数据结构为双向链表,支持快速增删 3.deque 底层数据结构为一个中央控制器和多个缓冲 ...

  2. C++ STL常用标准库容器入门(vector,map,set,string,list...)

    STL常用标准库容器 C++ STL中最基本以及最常用的类或容器无非就是以下几个: 目录 string vector deque list forward_list queue priority_qu ...

  3. C++常用数据结构或技巧

    C++常用数据结构 链表 内存的申请与释放 滑动窗口 前缀和/积与后缀和/积 差分数组 线段树 前缀树/字典树(Trie) 单调栈 单调队列 并查集 二叉树 创建二叉树 二叉树的遍历 二叉树遍历的变体 ...

  4. C++常用数据结构的实现

    常用数据结构与算法的实现.整理与总结 我将我所有数据结构的实现放在了github中:Data-Structures-Implemented-By-Me 常用数据结构与算法的实现.整理与总结 KMP字符 ...

  5. Python 基础(6)(常用数据结构)

    https://www.toutiao.com/a6634514748694069763/ 2018-12-14 08:10:00 常用数据结构 1)元组 元组是一种静态的数据结构,无法修改,若要修改 ...

  6. Python 基础常用数据结构

    2019独角兽企业重金招聘Python工程师标准>>> 常用数据结构 1)元组 元组是一种静态的数据结构,无法修改,若要修改只能重新生成新的元组. 输出结果: 元组元素的获取是通过索 ...

  7. 【Python基础】盘点 Python 10 大常用数据结构(上篇)

    我的施工之路 上图施工计划,已完成专题: 1我的施工计划 2数字专题 3字符串专题 4列表专题 5流程控制专题 6编程风格专题 7函数使用 8.面向对象编程(上篇) 9.面向对象编程(下篇) Pyth ...

  8. 【Python基础】盘点 Python 10 大常用数据结构(下篇)

    我的施工之路 虽然艰辛,却有读者们陪伴 Python 常用数据结构 此专题<盘点Python10大常用数据结构>目录: 学习目的 学习目标 1 list 2 tuple 3 set 4 d ...

  9. Python 基础(常用数据结构)

    常用数据结构 1)元组 元组是一种静态的数据结构,无法修改,若要修改只能重新生成新的元组. 输出结果: 元组元素的获取是通过索引值去获得的:例如上面的tup1[0]返回apple:另外你可以直接把tu ...

最新文章

  1. 在阿里云ECS服务器上面开启tomcat服务并且正常后,无法访问怎么办?原来是没有开通外网访问的端口
  2. 指针的本质--u_char*指针在Nginx源码中的应用及原因
  3. 关于学习Python的一点学习总结(32->隐藏及lambda)
  4. 检查压缩包是否损坏_修复损坏的gzip压缩文件之原理篇
  5. Mysql 解压版 安装时候的注意事项
  6. java基础之构造方法
  7. c 语言中三个函数,帮忙解释几个C语言中的函数?
  8. 开启php的ssl,php怎么开启ssl?开启ssl的方法
  9. FROONT – 超棒的可视化响应式网页设计工具
  10. 华为云mysql端口号_华为云云耀服务器远程连接mysql,报错10038端口配置问题。
  11. 数据库-MySQL-SQL语句
  12. FLEX Tree动态获得信息时遇到的问题总结
  13. python 中缩进—— tab 还是空格是不一样的,一般不能混用,除非设置Tab自动替换成空格
  14. matlab 响应曲面,MINITAB 响应曲面法应用
  15. 回归分析什么时候取对数_为什么相关或回归分析时 x和y取log
  16. VAST2.0视频广告投放解决方案改变视频网站未来技术格局
  17. PX4中四元数更新(毕卡求解法与一阶龙格库塔)
  18. 新生报到系统_中大深圳校区欢迎你!5个院系1271名本科新生报到
  19. 360浏览器的极速模式和兼容模式的区别
  20. 解决nodemon : 无法加载文件 C:\Users\admin\AppData\Roaming\npm\nodemon.ps1

热门文章

  1. vs2017 qt 修改exe图标没有更新成功
  2. mysql1060,非公RX 480对比GTX 1060哪个好?RX 480对比GTX 1060全面对比评测
  3. 新版神舟战神ZX9游戏本 评测
  4. 视频会议常用术语——转自华为TE40帮助文档
  5. Tensorflow tflearn
  6. 干货丨什么是SOA架构?SOA架构有什么作用?
  7. Android 保证Service服务不被杀死的几个方法
  8. 数字电子技术基础 原码 反码 补码及运算
  9. STM32F7普通定时器的使用(定时+中断+PWM)
  10. BRDF理论及shader实现(下)