C++STL初始

2.1STL的诞生

·长久以来,软件界一直希望建立一种可重复利用的东西

·C++的面向对象和泛型编程思想,目的就是复用性的提升

·大多情况下,数据结构和算法都未能有一套标准,导致被迫从事大量重复工作

·为了建立数据结构和算法的一套标准,诞生了STL

2.2STL基本概念

·STL(Standard Template Library,标准模板库)

·STL从广义上分为:容器(container)算法(algorithm)迭代器(iterator)

·容器和算法之间通过迭代器进行无缝连接

·STL几乎所有的代码都采用了模板或者模板函数

2.3STL六大组件

STL大体分为六大组件,分别是:容器、算法、迭代器、仿函数、适配器(配置器)、空间适配器

1、容器:各种3数据结构,如vector、list、deaque、set、map等,用来存放数据。

2、算法:各种常用的算法,如sort、find、copy、for_each等

3、迭代器:扮演了容器与算法之间的胶合剂。

4、仿函数:行为类似函数,可作为算法的某种策略。

5、适配器:一种用来修饰容器或者仿函数或迭代器接口的东西

6、空间配置器:负责空间的配置与管理。

2.4STL中容器、算法、迭代器

容器:置物之所也

STL容器就是将运用最广泛的一些数据结构实现出来

常用的数据结构:数组,链表,树,栈,队列,集合,映射表,等

这些容器分为序列式容器和关联式容器两种:

    序列式容器:强调值得排序,序列式容器中的每个元素均有固定的位置

    关联式容器:二叉树结构,各元素之间没有严格的物理上的顺序关系

算法:问题之解决也

有限的步骤,解决逻辑或数学上的问题,这一门学科我们叫做算法(Alogorithms)

算法分为:质变算法和非质变算法。

质变算法:是指运算过程中会更改区间内的元素的内容。例如拷贝,替换,删除等等

非质变算法:是指运算过程中不会更改区间内的元素内容,例如查找、计数、遍历、寻找极值等等

算法:问题之解决也

有限的步骤,解决逻辑或数学上的问题,这一门学科我们叫做算法(Algorithms)

算法分为:质变算法和非质变算法。

质变算法:是指运算过程中会更改区间的元素的内容。例如拷贝,替换,删除等等

非质变算法:是指运算过程中不会更改区间内的元素内容,例如查找、计数、遍历、寻找极值等等

迭代器:容器和算法之间粘合剂

提供一种方法,使之能够依序寻访某个容器所含的各个元素,而又无需暴露该容器的内部表示方式。

每个容器都有自己专属的迭代器

迭代器使用非常类似于指针,初学阶段我们可以先理解迭代器为指针

常用的容器中迭代器种类为双向迭代器,和随机访问迭代器

2.5容器算法迭代器初始

了解STL中容器、算法、迭代器概念之后,我们利用代码感受STL的魅力

STL中最常见用的容器为vector,可以理解为数组,下面我们将学习如何向这个容器中插入数据,并遍历这个容器

2.5.1vector存放内置数据类型

容器:vector

算法:for_each

迭代器:vector<int>::iterator

 2.5.2 Vector存放自定义数据类型

学习目标:vector中存放自定义数据类型,并且打印输出

 2.5.3 Vector容器嵌套容器

学习目标:容器中嵌套容器,我们将所有数据进行遍历输出

 3.1.1 string基本概念

本质:

·string是C++风格的字符串,而string本质是一个类

string和char*区别:

·char*是一个指针

·string是一个类,类内部封装了char*,管理这个字符串是一个char*型的容器。

特点:

string类内封装了很多成员方法

例如:查找find,拷贝copy,删除delete替换replace,插入insert

string管理char*所分配的内存,不用担心复制越界和取值越界等,由类内部进行负责

3.1.2string构造函数

 

总结:string的多种构造方式没有可比性,灵活使用即可

3.1.3string赋值操作

功能描述:

·给string字符串进行赋值

赋值的函数原型:

总结 :

string的赋值方式很多,operator=这种方式是比较实用的

3.1.4string字符串拼接

功能描述:

·实现在字符串末尾拼接字符串

函数原型:

·string& operator+=(const char* str)//重载+=操作符

·string& operator+=(const char c);//重载+=操作符

·string& operator+=(const string& str);//重载+=操作符

·string& append(const char* s);//把字符串s连接到当前字符串结尾

·string& append(const char* s,int n);//把字符串s的前n个字符连接到当前字符串结尾

·string& append(const string &s);//同operator+=(const string& str)

`stringI& append(const string& s,int pos,int n);//字符串s中从pos开始的n个字符连接到字符串结尾

总结:字符串拼接的重载版本很多,初学阶段记住几种即可

3.1.5 string 查找和替换

功能描述:

·查找:查找指定字符串是否存在

·替换:在指定的位置替换字符串

函数原型:

·int find(const string& str,int pos=0) const;//查找str第一次出现位置,从pos开始查找

·int find(const char* s,int pos=0) const;//查找s第一次出现位置,从pos开始查找

·int find(const char* s,int pos,int n) const;//从pos位置查找s的前n个字符第一次位置

·int find(const char c,int pos=npos) const;//查找字符c第一次出现位置

·int rfind(const string& str,int pos=npos) const;//查找str 最后一次位置,从pos开始查找

·int rfind(const char* s,int pos=npos) const;//查找s 最后一次位置,从pos开始查找

·int rfind(const char* s,int pos,int n)const;//从pos查找s的前n个字符最后一次位置

·int rfind(const char c,int pos=0) const;//查找字符c最后一次出现位置

·string& replace(int pos,int n,const string& str);//替换从pos开始n个字符为字符串str

·string& replace(int pos,int n,const char* s);//替换从pos开始的n个字符为字符串s

总结:

·find查找是从左往右,rfind从右往左

·find找到字符串后返回查找的第一个字符位置,找不到返回-1

·replace在替换时,要指定从哪个位置起,多少个字符,替换成什么样的字符串 

3.1.6 string字符串比较

功能描述:

·字符串之间的比较

比较方式:

·字符串比较是按字符的ASCLL码进行对比

=返回· 0

>返回 1

<返回 -1

函数原型:

·int compare(const string& s)const;//与字符串s比较

·int compare(const char* s)const;//与字符串s比较

 总结:字符串对比主要用于比较两个字符串是否相等,判断谁大谁小的意义并不是很大

3.1.7string 字符存取

string中单个字符存取方式有两种

·char& operator[](int n);//通知[]方式取字符

·char& at(int n);//通过at方法获取字符

 总结:string字符串中单个字符存取有两种方式,利用[]或at

3.1.8string插入和删除

功能描述:

·对string字符串进行插入和删除字符操作

函数原型:

·string& insert(int pos,const char* s);//插入字符串

·string& inrsert(int pos,const string& str);//插入字符串

·string& erase(int pos,int n=npos);//删除从Pos开始的n个字符

总结:插入和删除的起始下标都是从0开始 

3.1.9string子串

功能描述:

·从字符串中获取想要的子串

函数原型:

·string substr(int pos=0,int n=npos)const;//返回由pos开始的n个字符组成的字符串

 总结:灵活的运用求子串功能,可以在实际开发中获取有效信息

3.2 vector容器

3.2.1 vector基本概念

功能:

·vector数据结构和数组非常相似,也称为单端数组

vector与普通数组区别:

·不同之处在于数组是静态空间,而vector可以动态扩展

动态扩展:

·并不是在原空间之后续接新空间,而是找更大的内存空间,然后将原数据拷贝新空间,释放原空间

·vector容器的迭代器是支持随机访问的迭代器

3.2.2 vector构造函数

功能描述:

·创建vector容器

函数原型:

·vector<T>v;//采用模板实现类,实现默认构造函数

·vector(v.begin(),v.end());//将v[begin(),end()]区间中的元素拷贝给本身

·vector(n,elem);//构造函数将n个elem拷贝给本身

·vector(const vector &vec)//拷贝构造函数

总结:vector的多种构造方式没有可比性,灵活使用即可 

3.2.3 vector赋值操作

功能描述:
·给vector容器进行赋值

函数原型:

·vector& operator=(const vector &vec);//重载等号操作符

·assign(beg,end);//将[beg,end]区间中的数据拷贝赋值给本身

·assgin(n,elem);//将n个elem拷贝赋值给本身

总结:vector赋值方式比较简单,使用operator=,或者assign都可以

3.2.4 vector容器和大小

·对vector容器的容量的大小操作

函数原型:

·empty();//判断容器是否为空

·capacity();//容器的容量

 ·size();//返回容器中元素的个数

·resize(int num,elem);//重新指定容器的长度为num,若容器变长,则以elem值填充新位置。

                                  //如果容器变短,则末尾超出容器长度的元素被删除

总结:

·判断是否为空---empty

·返回元素个数---size

`返回容器容量---capacity

`重新指定大小---resize

3.2.5 vector插入和删除

功能描述:

·对vector容器进行插入、删除操作

函数原型:

·push_back(ele);//尾部插入元素ele

·pop_back();//删除最后一个元素

·insert(const_iterator pos,ele);//迭代器指向位置pos插入元素ele

·insert(const_iterator pos,int count,ele);//迭代器指向位置pos插入count个元素ele

·erase(const_iterator pos);//删除迭代器指向的元素

·erase(const_iterator start,const_iterator end);//删除迭代器从start到end之间的元素

·clear();//删除容器中所有元素

 

总结:

`尾插--push_back

`尾删---pop_back

`插入---insert(位置迭代器)

·删除---erase(位置迭代器)

·清空---clear

3.2.6 vector数据存储 

功能描述:

·对vector中的数据的存取操作

函数原型:

·at(int idx);//返回索引idx所指的数据

·operator[];//返回索引idx所指的数据

·front();//返回容器中第一个数据元素

·back();//返回容器中最后一个数据元素

总结:

·除了用迭代器获取vector容器中元素,[]和at也可以

·front返回容器第一个元素

·back返回容器最后一个元素 

3.2.7 vector互换容器

功能描述:

·实现两个容器内元素进行互换

函数原型:

·swap(vec);//将vec与本身的元素互换

 总结;swap可以使两个容器互换,可以达到实用的收缩内存效果

3.2.8 vector预留空间

功能描述:

·减少vector在动态扩展容量时的扩展次数

函数原型:

·reserve(int len);//容器预留len个元素长度,预留位置不初始化,元素不可访问。

总结:如果数据量较大,可以一开始利用reserve预留空间 

3.3 deque容器

3.3.1 deque容器基本概念

功能:

·双端数组,可以对头端进行插入删除操作

deque与vector区别:

·vector对于头部的插入删除效率低,数据量大,效率越低

·deque相对而言,对头部的插入删除速度会比vector快

·vector访问元素时的速度会比deque快,这和两者内部实现有关

deque内部工作原理:

deque内部有个中控器,维护每段缓冲区中的内容,缓冲区中存放真实数据中控器维护的是每个缓冲区的地址,使得使用deque时像一片连续的内存空间

·deque容器的迭代器也是支持随机访问的

3.2.2 deque构造函数

功能描述;

·deque容器构造

函数原型:

·deque<T>deqT;//默认构造形式

·deque(beg,end);//构造函数将[beg,end)区间中的元素拷贝给本身。

·deque(n,elem);//构造函数将n个elem拷贝给本身。

·deque(const deque &deq);//拷贝构造函数

总结:deque容器和vector容器的构造方式几乎一致,灵活使用即可beg

3.3.3 deque赋值操作

功能描述:

·给deque容器进行赋值

函数原型:

·deque&-operator=(const deque &deq);//重载等号操作符

·assgin(beg,end);//将[beg,end)区间中的数据拷贝赋值给本身

·assign(n,elem);//将n个elem拷贝赋值给本身

总结:deque赋值操作也与vector相同,需熟练掌握 

3.3.4 deque大小操作

功能描述:

·对deque容器的大小进行操作

函数原型:

·deque.empty();//判断容器是否为空

·deque.size();//返回容器中元素个数

·deque.resize(num);//重新指定容器的长度为num,若容器变长,则默认值填充新位置

                                //如果容器变短,则末尾超出容器长度的元素被删除

·deque.resize(num,elem);//重新指定容器的长度为num,若容器变长,则以elem值填充新位置

                                        //如果容器变短,则末尾超出容器长度的元素被删除。

总结:

·deque没有容量的概念

·判断是否为空---empty

·返回元素个数---size

·重新指定个数---resize 

3.3.5 deque插入和删除

功能描述:

·向deque容器插入和删除数据

函数原型:

两端插入操作:

·push_back(elem);//在容器尾部添加一个数据

·push_front(elem);//在容器头部插入一个数据

·pop_back();//删除容器最后一个数据

·pop_front();//删除容器第一个数据

指定位置操作:

·insert(pos,elem);//在pos位置插入一个elem元素的拷贝,返回新数据的位置。

·insert(pos,n,elem);//在pos位置插入n个elem数据,无返回值。

`insert(pos,beg,end);//在pos位置插入[beg,end)区间的数据,无返回值。

·clear();//清空容器的所有数据

·erase(beg,end);//删[beg,end)区间的数据,返回下一个数据的位置

·erase(pos);//删除pos位置的数据,返回下一个数据的位置

 总结:

·插入和删除提供的位置是迭代器!

·尾插---push_back

·尾删---pop_back

·头删---pup_front

·头删---pop_front

3.3.6 deque数据存取

功能描述:

·对deque中的数据的存取操作

函数原型:

·at(int idx);//返回索引idx所指的数据

·operator[];//返回索引idx所指的数据

·front();//返回容器中第一个数据元素

·back();//返回容器中最后一个数据元素

总结:

·除了用迭代器获取deque容器中元素,[]和at也可以

`front返回容器第一个元素

·back返回容器最后一个元素

3.3.7 deque排序

功能描述:

·利用算法实现对deque容器进行排序

算法:

·sort(iterator beg,iterator end)//对beg和end区别内元素进行排序

总结:sort算法非常实用,使用时包含头文件algorithm即可 

3.4案例-评委打分

3.4.1案例描述

有5名选手:ABCDE,10个评委分别对每一名选手打分,去除最高分,去除评委中最低分,取平均分。

3.4.2实现步骤

1、创建五名选手,放到vector中

2、遍历vector容器,取出来每一个选手,执行for循环,可以把10个评分打分存到deque容器中

3、sort算法对deque容器中分数排序,去除最高分和最低分

4、deque容器遍历一遍,累加总分

5、获取平均分

3.5 stack容器

3.5.1 stack基本概念

概念:stack是一种先进后出(First in Last Out,FILO)的数据结构,它只有一个出口

栈中只有顶端的元素才可以被外界使用,因此栈不允许有遍历行为

栈中进数据称为---入栈push

栈中弹出数据称为---出栈 pop

3.5.2 stack 常见接口

功能描述:栈容器常用的对外接口

构造函数:

·stack<T> stk;//stack采用模板类实现,stack对象的默认构造形式

·stack(const stack &stk);//拷贝构造函数

赋值操作:

·stack& operator=(const stack& stk);//重载等号操作符

数据存取:

·push(elem);//向栈顶添加元素

·pop();//从栈顶移除第一个元素

top();//返回栈顶元素

大小操作:

·empty();//判断堆栈是否为空

·size();//返回栈的大小

总结:

·入栈---push

·出栈---pop

·返回栈顶---top

·判断栈是否为空---empty

·返回栈大小---size

3.6 queue容器

3.6.1 queue基本概念

概念:Queue是一种先进先出(First In First Out,FIFO)的数据结构,它有两个出口

 队列容器允许从一端新增元素,从另一端移除元素

队列中只有队头和队尾才可以被外界使用,因此队列不允许有遍历行为

队列中进数据称为---入队 push

队列中出数据称为---出队 pop

3.6.2 queue 常见接口

功能描述:栈容器常用的对外接口

构造函数:

·queue<T> que;//queue采用模板类实现,queue对象的默认构造形式

·queue(const queue& que);//拷贝构造函数

赋值操作:

·queue& operator=(const queue& que);//重载等号操作符

数据存取:

·push(elem);//往队尾添加元素

·pop();//从队头移除第一个元素

·back();//返回最后一个元素

·front();//返回第一个元素

大小操作:

·empty();//判断堆栈是否为空

·size();//返回栈的大小

总结:

·入队---push

·出队---pop

·返回队头元素---front

·返回队尾元素---back

·判断队是否为空---empty

· 返回队列大小---size

3.7 list容器

3.7.1 list基本概念

功能:将数据进行链式存储

链表(list)是一种物理存储单元上非连续的存储结构,数据元素的逻辑顺序是通过链表中的指针链接实现的

链表的组成:链表由一系列结点组成

结点的组成:一个是存储数据元素的数据域,另一个是存储下一个结点地址的指针域

STL中的链表是一个双向循环链表

由于链表的存储方式并不是连续的内存空间,因此链表list中的迭代器只支持前移和后移,属于双向迭代器

list的优点:

·采用动态存储分配,不会造成内存浪费和溢出

·链表执行插入和删除操作十分方便,修改指针即可,不需要移动大量元素

list的缺点:

·链表灵活,但是空间(指针域)和时间(遍历)额外耗费较大

List有一个重要的性质,插入操作和删除操作都不会造成原有list迭代器的失效,这在vector是不成立的。

总结:STLList和vector是两个最常被使用的容器,各有优缺点

3.7.2list构造函数

功能描述:

·创建list容器

函数原型:

·list<T>lst;//list采用模板类实现,对象的默认构造形式;

·list(beg,end);//构造函数将[beg,end)区间中的元素拷贝给本身。

·list(n,elem);//构造函数将n个elem拷贝给本身。

·list(const list &lst);//拷贝构造函数。

总结:list构造方式同其他几个STL常用容器,熟练掌握即可 

3.7.3list赋值和交换

功能描述:

·给list容器进行赋值,以及交换list容器

函数原型:

·assgin(beg,end);//将[beg,end);//将[beg,end)区间中的数据拷贝赋值给本身

·assign(n,elem);//将n个elem拷贝赋值给本身

·list& operator=(const list &lst);//重载等号操作符

·swap(list);//将lst与本身的元素交换

 总结:list赋值和交换操作能够灵活运用即可

3.7.4list大小操作

功能描述:

·对list容器大小进行操作

函数原型:

·size();//返回容器中元素的个数

·empty();//判断容器是否为空

·resize(num);//重新指定容器的长度为num,若容器变长,则以默认值填充新位置

                     //如果容器变短,则末尾超出容器长度的元素被删除。

·resize(num,elem);//重新指定容器的长度为num,若容器变长,则以elem值填充新位置。

                             //如果容器变短,则末尾超出容器长度的元素被删除。

总结:

·判断是否为空---empty

·返回元素个数---size

·重新指定个数---resize

 3.7.5 list插入和删除

功能描述:

·对list容器进行数据的插入和删除

函数原型:

·push_back(elem);//在容器尾部加入一个元素

·pop_back();//删除容器中最后一个元素

·push_front(elem);//在容器开头插入一个元素

·pop_front();//从容器开头移除第一个元素

·insert(pos,elem);//在pop位置插elem元素的拷贝,返回新数据的位置

·insert(pos,n,elem);//在pos位置插入n个elem数据,无返回值。

·insert(pos,beg,end);//在pos位置插入[beg,end)区间的数据,无返回值。

·clear();//移除容器的所有数据

·erase(beg,end);//删除[beg,end)区间的数据,返回下一个数据的位置。

·erase(pos);//删除pos位置的数据,返回下一个数据的位置

·remove(elem);//删除容器中所有与elem值匹配的元素。

总结:

·尾插---push_back

·尾删---pop_back

·头插---push_front

·头删---push_back

·插入---insert

·删除---erase

·移除---remove

·清空---clear

3.7.6 list数据存取

功能描述:

·对list容器中数据进行存取

函数原型:

·front();//返回第一个元素

·back();//返回最后一个元素

总结:

·list容器中不可以通过[]或者at方式访问数据

·返回第一个元素---front

`返回最后一个元素---back 

 3.7.7 list反转和排序

功能描述:

·将容器中的元素反转,以及将容器中的数据进行排序

函数原型:

·reverse();//反转链表

·sort();//链表排序

总结:

·反转---reverse

·排序---sort(成员函数)

3.7.8 排序案例

案例描述:将Person自定义数据类型进行排序,Perosn中属性有姓名、年龄、身高

排序规则:按年龄进行升序、如果年龄相同按照身高进行排序

总结:

·对于自定义数据类型,必须要指定排序规则,否则编译器不知道如何进行排序

·高级排序只是在排序规则上再进行一次逻辑规则制定,并不复杂 

3.8 set/multiset容器

3.8.1 set基本概念

简介:

·所有元素都会在插入时自动被排序

本质:

·set/multiset属于关联式容器,底层结构是用二叉树实现。

set和multise区别:

·set不允许容器中有重复的元素

·multiset允许容器中有重复的元素

3.8.2 set构造和赋值

功能描述:创建set容器以及赋值

构造:

·set<T>st;//默认构造函数;

·set(const set &st);//拷贝构造函数

赋值:

·set& operator=(const set &st);//重载等号操作符

总结:

·set容器插入数据时用insert

·set容器插入数据的数据会自动排序

3.8.3 set大小和交换 

功能描述:

·统计set容器大小以及交换set容器

函数原型:

·size();//返回容器中元素的数目

·empty();//判断容器是否为空

·swap(st);//交换两个集合容器

总结:

·统计大小--size

`判断是否为空---empty

·交换容器---swap

3.8.4 set插入和删除

功能描述:

· set容器进行插入数据和删除数据

函数原型:

·insert(elem);//在容器中插入元素

·clear();//清除所有元素

·erase(pos);//删除pos迭代器所指的元素,返回下一个元素迭代器。

·erase(beg,end);//删除区间[beg,end)的所有元素,返回下一个元素的迭代器。

·erase(elem);//删除容器中值为elem的元素

总结:

·插入---insert

·删除---erase

·清空---clear 

3.8.5 set查找和统计

功能描述:

·对set容器进行查找数据以及统计数据

函数原型:

·find(key);//查找key是否存在,若存在,返回该键的元素的迭代器,若不存在返回set.end();

·count(key);//统计key的元素个数

总结:

·查找---find(返回的是迭代器)

·统计---count(对于set,结果为0或者1)

3.8.6 set和multiset的区别

区别:

·set不可以插入重复数据,而multiset可以

·set插入数据的同时会返回插入结果,表示插入是否成功

·multiset不会检测数据,因此可以插入重复数据

总结:

·如果不允许插入重复数据可以利用set

·如果需要插入重复数据利用multiset

3.8.7 pair对组创建

功能描述:

·成对出现的数据,利用对组可以返回两个数据

两种创建方式:

·pair<type,type>p(value1,value2);

·pair<type,type>p=make_pair(value1,value2);

总结:

两种方式都可以创建数组,记住一种即可 

3.8.8 set容器排序

学习目标:

·set容器默认排序规则为从小到大,掌握如何改变排序规则

主要技术点:

·利用仿函数。可以改变排序规则

示例一 set存放内置数据类型

总结:利用仿函数可以指定set容器的排序规则 

示例二:set存放自定义数据类型

总结:对于自定义数据类型,set必须指定排序规则才可以插入数据

3.9map/multimap

3.9.1map基本概念

简介:

·map中所有元素都是pair

·pair中第一个元素为key(键值),起到索引作用,第二个元素为value(实值)

·所有元素都会根据元素的键值自动排序

本质:

·map/multimap属于关联式容器,底层结构是用二叉树实现

优点:

·可以根据key值快速找到value值

map和multimap区别:

·map不允许容器中有重复key元素

·multimap允许容器中有重复key值元素 

3.9.2 map构造和赋值

功能描述:

·对map容器进行构造和赋值操作

函数原型:

构造:

·map<T1,T2>mp;//map默认构造函数;

·map(const map &mp);//拷贝构造函数

赋值:

·map& operator=(const map &mp);//重载等号操作符

总结:map中所有元素都是成对出现,插入数据时候要使用对组 

3.9.3 map大小和交换

功能描述:

·统计map容器以及交换map容器

函数原型:

·size();//返回容器中元素的数目

·empty();//判断容器是否为空

·swap(st);//交换两个集合容器

总结:

·统计大小---size

·判断是否为空---empty

·交换容器---swap

3.9.4 map插入和删除

·map容器进行插入数据和删除数据

函数原型:

·insert(elem);//在容器中插入元素。

·clear();//清除所有元素

·erase(pos);//删除pos迭代器所指的元素,返回下一个元素的迭代器。

erase(beg,end);//删除区间[beg,end)的所有元素,返回下一个元素的迭代器。

·erase(key);//删除容器中值为key的元素。

总结:

·map插入方式很多,记住其一即可

·插入---insert

·删除---erase

·清空---clear 

3.9.5 map查找和统计

功能描述:

·对map容器进行查找数据以及统计数据

函数原型:

·find(key);//查找key是否存在,返回该键的元素的迭代器,若不存在,返回map.end();

·count(key);//统计key的元素个数

总结:

·查找---find(返回的是迭代器)

·统计---count(对于map,结果为0或者为1)

3.9.6 map容器排序

学习目标:

·map容器默认排序规则为按照key值进行从小到大排序,掌握如何改变排序规则

主要技术点:

·利用仿函数,可以改变排序规则
 

总结:

·利用仿函数可以指定map容器的排序规则

·对于自定义数据类型,map必须要指定排序规则,同set容器

3.10案例-员工分组

3.10.1 案例描述

·公司今天招聘了10个员工(ABCDEFGHIJ),10名员工进入公司之后,需要指派员工在那个部门工作

·员工信息有:姓名 工资组成:部门分为:策划、美术、研发

·随机给10个员工分配部门和工资

·通过multimap进行信息的插入 key(部门编号)value(员工)

·分部门显示员工信息

3.10.2 实现步骤

1.创建10名员工,放到vector中

2.遍历vector容器,取出每个员工,进行随机分组

3.分组后,将员工部门编号作为key,具体员工作为value,放入到multimap容器中

4.分部门显示员工信息

 

4 STL-函数对象

4.1函数对象

4.1.1函数对象概念

概念:

·重载函数调用操作符的类,其对象称称为函数对象

·函数对象使用重载的()时,行为类似函数调用,也叫仿函数

本质:

函数对象(仿函数)是一个类,不是一个函数

4.1.2 函数对象使用

特点:

·函数对象在使用时,可以像普通函数那样调用,可以有参数,可以有返回值

·函数对象超出普通函数的概念吗,函数对象可以有自己的状态

·函数对象可以作为参数传递

 总结:

仿函数写法非常灵活,可以作为参数进行传递

4.2谓词

4.2.1谓词概念

概念:

·返回bool类型的仿函数称为谓词

·如果operator()接受一个参数,那么叫做一元谓词

·如果operator()接受两个参数,那么叫做二元谓词

总结:参数只有一个的谓词,称为一元谓词

总结:参数只有两个的谓词,称为二元谓词 

4.3内建函数对象

4.3.1 内建函数对象意义

概念:

·STL内建了一些函数对象

分类:

·算术仿函数

·关系仿函数

·逻辑仿函数

用法:

·这些仿函数所产生的对象,需要引入头文件#include<functional>

4.3.2 算术仿函数

功能描述:

·实现四则运算

·其中negate是一元运算,其他都是二元运算

仿函数原型:

·template<class T>T pius<T>//加法仿函数

·template<class T>T minus<T>//减法仿函数

·template<class T>T multiplies<T>//乘法仿函数

·template<class T>T divides<T>//除法仿函数

·template<class T>T modulus<T>//取模仿函数

·template<class T>T negate<T>//取反仿函数

总结:使用内建函数对象时,需要引入头文件#include<functional> 

4.3.3 关系仿函数

功能描述:

·实现关系对比

仿函数原型:

·template<class T>bool equal_to<T>//等于

·template<class T>bool not_equal_to<T>//不等于

·template<class T>bool greater<T>//大于

·template<class T>bool greater_equal<T>//大于等于

·template<class T> bool less<T> //小于

·template<class T> bool less_equal<T> //小于等于

 总结:关系运算仿函数最常见的就是greater<>大于

4.3.4 逻辑仿函数


功能描述:
实现逻辑运算
函数原型:
·template<class T> bool logical_and<T> //逻辑与
·template<class T> bool logical_or<T> //逻辑或
·template<class T> bool logical_not<T> //逻辑非

总结:逻辑仿函数实际应用较少,了解即可 

5 STL- 常用算法

概述:

  • 算法主要是由头文件&lt;algorithm&gt; &lt;functional&gt; &lt;numeric&gt;组成。

  • &lt;algorithm&gt;是所有STL头文件中最大的一个,范围涉及到比较、 交换、查找、遍历操作、复制、修改等等

  • &lt;numeric&gt;体积很小,只包括几个在序列上面进行简单数学运算的模板函数

  • &lt;functional&gt;定义了一些模板类,用以声明函数对象。

5.1 常用遍历算法

学习目标:

  • 掌握常用的遍历算法

算法简介:

  • for_each //遍历容器
  • transform //搬运容器到另一个容器中
5.1.1 for_each

功能描述:

  • 实现遍历容器

函数原型:

  • for_each(iterator beg, iterator end, _func);

    // 遍历算法 遍历容器元素

    // beg 开始迭代器

    // end 结束迭代器

    // _func 函数或者函数对象

  • 总结:for_each在实际开发中是最常用遍历算法,需要熟练掌握

  • 5.1.2 transform

    功能描述:

  • 搬运容器到另一个容器中
  • 函数原型:

  • transform(iterator beg1, iterator end1, iterator beg2, _func);
  • //beg1 源容器开始迭代器

    //end1 源容器结束迭代器

    //beg2 目标容器开始迭代器

    //_func 函数或者函数对象

     

    总结:搬运的目标容器必须要提前开辟空间,否则无法正常搬运 

5.2 常用查找算法

学习目标:

  • 掌握常用的查找算法

算法简介:

  • find //查找元素
  • find_if //按条件查找元素
  • adjacent_find //查找相邻重复元素
  • binary_search //二分查找法
  • count //统计元素个数
  • count_if //按条件统计元素个数

5.2.1 find

功能描述:

  • 查找指定元素,找到返回指定元素的迭代器,找不到返回结束迭代器end()

函数原型:

  • find(iterator beg, iterator end, value);

    // 按值查找元素,找到返回指定位置迭代器,找不到返回结束迭代器位置

    // beg 开始迭代器

    // end 结束迭代器

    // value 查找的元素

  • 总结:利用find可以在容器中找到指定的元素,返回值是迭代器 

5.2.2 find_if

功能描述:

  • 按条件查找元素

函数原型:

  • find_if(iterator beg, iterator end, _Pred);

    // 按值查找元素,找到返回指定位置迭代器,找不到返回结束迭代器位置

    // beg 开始迭代器

    // end 结束迭代器

    // _Pred 函数或者谓词(返回bool类型的仿函数)

  • 5.2.3 adjacent_find

    功能描述:

  • 查找相邻重复元素
  • 函数原型:
  • adjacent_find(iterator beg, iterator end);

    // 查找相邻重复元素,返回相邻元素的第一个位置的迭代器

    // beg 开始迭代器

    // end 结束迭代器

  •  总结:面试题中如果出现查找相邻重复元素,记得用STL中的adjacent_find算法

5.2.4 binary_search

功能描述:

  • 查找指定元素是否存在

函数原型:

  • bool binary_search(iterator beg, iterator end, value);

    // 查找指定的元素,查到 返回true 否则false

    // 注意: 在无序序列中不可用

    // beg 开始迭代器

    // end 结束迭代器

    // value 查找的元素

总结:二分找法查找效率很高,值得注意的是查找的容器中元素必须的有序序列

5.2.5 count

功能描述:

  • 统计元素个数

函数原型:

  • count(iterator beg, iterator end, value);

    // 统计元素出现次数

    // beg 开始迭代器

    // end 结束迭代器

    // value 统计的元素

总结:统计自定义数据类型时候,需要配合重载operator==

5.2.6 count_if

功能描述:

  • 按条件统计元素个数

函数原型:

  • count_if(iterator beg, iterator end, _Pred);

    // 按条件统计元素出现次数

    // beg 开始迭代器

    // end 结束迭代器

    // _Pred 谓词

总结:按值统计用count,按条件统计用count_if

5.3 常用排序算法

学习目标:

  • 掌握常用的排序算法

算法简介:

  • sort //对容器内元素进行排序
  • random_shuffle //洗牌 指定范围内的元素随机调整次序
  • merge // 容器元素合并,并存储到另一容器中
  • reverse // 反转指定范围的元素

5.3.1 sort

功能描述:

  • 对容器内元素进行排序

函数原型:

  • sort(iterator beg, iterator end, _Pred);

    // 按值查找元素,找到返回指定位置迭代器,找不到返回结束迭代器位置

    // beg 开始迭代器

    // end 结束迭代器

    // _Pred 谓词

 

总结:sort属于开发中最常用的算法之一,需熟练掌握

5.3.2 random_shuffle

功能描述:

  • 洗牌 指定范围内的元素随机调整次序

函数原型:

  • random_shuffle(iterator beg, iterator end);

    // 指定范围内的元素随机调整次序

    // beg 开始迭代器

    // end 结束迭代器

 

总结:random_shuffle洗牌算法比较实用,使用时记得加随机数种子

5.3.3 merge

功能描述:

  • 两个容器元素合并,并存储到另一容器中

函数原型:

  • merge(iterator beg1, iterator end1, iterator beg2, iterator end2, iterator dest);

    // 容器元素合并,并存储到另一容器中

    // 注意: 两个容器必须是有序的

    // beg1 容器1开始迭代器

  • // end1 容器1结束迭代器

  • // beg2 容器2开始迭代器

  • // end2 容器2结束迭代器

  • // dest 目标容器开始迭代器

     

 总结:merge合并的两个容器必须的有序序列

5.3.4 reverse

功能描述:

  • 将容器内元素进行反转

函数原型:

  • reverse(iterator beg, iterator end);

    // 反转指定范围的元素

    // beg 开始迭代器

    // end 结束迭代器

 

 总结:reverse反转区间内元素,面试题可能涉及到

5.4 常用拷贝和替换算法

学习目标:

  • 掌握常用的拷贝和替换算法

算法简介:

  • copy // 容器内指定范围的元素拷贝到另一容器中
  • replace // 将容器内指定范围的旧元素修改为新元素
  • replace_if // 容器内指定范围满足条件的元素替换为新元素
  • swap // 互换两个容器的元素

5.4.1 copy

功能描述:

  • 容器内指定范围的元素拷贝到另一容器中

函数原型:

  • copy(iterator beg, iterator end, iterator dest);

    // 按值查找元素,找到返回指定位置迭代器,找不到返回结束迭代器位置

    // beg 开始迭代器

    // end 结束迭代器

    // dest 目标起始迭代器

总结:利用copy算法在拷贝时,目标容器记得提前开辟空间

5.4.2 replace

功能描述:

  • 将容器内指定范围的旧元素修改为新元素

函数原型:

  • replace(iterator beg, iterator end, oldvalue, newvalue);

    // 将区间内旧元素 替换成 新元素

    // beg 开始迭代器

    // end 结束迭代器

    // oldvalue 旧元素

    // newvalue 新元素

 

总结:replace会替换区间内满足条件的元素

5.4.3 replace_if

功能描述:

  • 将区间内满足条件的元素,替换成指定元素

函数原型:

  • replace_if(iterator beg, iterator end, _pred, newvalue);

    // 按条件替换元素,满足条件的替换成指定元素

    // beg 开始迭代器

    // end 结束迭代器

    // _pred 谓词

    // newvalue 替换的新元素

 

总结:replace_if按条件查找,可以 利用仿函数灵活筛选满足的条件

5.4.4 swap

功能描述:

  • 互换两个容器的元素

函数原型:

  • swap(container c1, container c2);

    // 互换两个容器的元素

    // c1容器1

    // c2容器2

 

总结:swap交换容器时,注意交换的容器要同种类型

5.5 常用算术生成算法

学习目标:

  • 掌握常用的算术生成算法

注意:

  • 算术生成算法属于小型算法,使用时包含的头文件为 #include &lt;numeric&gt;

算法简介:

  • accumulate // 计算容器元素累计总和

  • fill // 向容器中添加元素

5.5.1 accumulate

功能描述:

  • 计算区间内 容器元素累计总和

函数原型:

函数原型:

  • accumulate(iterator beg, iterator end, value);

    // 计算容器元素累计总和

    // beg 开始迭代器

    // end 结束迭代器

    // value 起始值

  • 总结:accumulate使用时头文件注意是numeric,这个算法很实用

  • 5.5.2 fill

    功能描述:

  • 向容器中填充指定的元素
  • 函数原型:
  • fill(iterator beg, iterator end, value);

    // 向容器中填充元素

    // beg 开始迭代器

    // end 结束迭代器

    // value 填充的值

  •  

    总结:利用fill可以将容器区间内元素填充为 指定的值

  • 5.6 常用集合算法

    学习目标:

  • 掌握常用的集合算法
  • 算法简介:

  • set_intersection // 求两个容器的交集

  • set_union // 求两个容器的并集

  • set_difference // 求两个容器的差集

    5.6.1 set_intersection

    功能描述:

  • 求两个容器的交集
  • set_intersection(iterator beg1, iterator end1, iterator beg2, iterator end2, iterator dest);

    // 求两个集合的交集

    // 注意:两个集合必须是有序序列

    // beg1 容器1开始迭代器

  • // end1 容器1结束迭代器

  • // beg2 容器2开始迭代器

  • // end2 容器2结束迭代器

  • // dest 目标容器开始迭代器

  •  总结:

  • 求交集的两个集合必须的有序序列

  • 目标容器开辟空间需要从两个容器中取最小值

  • set_intersection返回值既是交集中最后一个元素的位置

5.6.2 set_union

功能描述:

  • 求两个集合的并集

函数原型:

  • set_union(iterator beg1, iterator end1, iterator beg2, iterator end2, iterator dest);

    // 求两个集合的并集

    // 注意:两个集合必须是有序序列

    // beg1 容器1开始迭代器

  • // end1 容器1结束迭代器

  • // beg2 容器2开始迭代器

  • // end2 容器2结束迭代器

  • // dest 目标容器开始迭代器

  • 总结:

  • 求并集的两个集合必须的有序序列

  • 目标容器开辟空间需要两个容器相加

  • set_union返回值既是并集中最后一个元素的位置

  • 5.6.3 set_difference

    功能描述:

  • 求两个集合的差集
  • 函数原型:
  • set_difference(iterator beg1, iterator end1, iterator beg2, iterator end2, iterator dest);

    // 求两个集合的差集

    // 注意:两个集合必须是有序序列

    // beg1 容器1开始迭代器

  • // end1 容器1结束迭代器

  • // beg2 容器2开始迭代器

  • // end2 容器2结束迭代器

  • // dest 目标容器开始迭代器

  • 总结:

  • 求差集的两个集合必须的有序序列

    目标容器开辟空间需要从两个容器取较大值

    set_difference返回值既是差集中最后一个元素的位置

     

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值