目录
容器
1.STL提供了如下核心内容
容器
迭代器
算法
2.容器--》用来装东西(数据)
(1)vector --》向量,本质是个大小可变的数组
#include <vector>
常用方法:
data() //返回指向容器首元素的地址
emplace(迭代器指定位置,新的元素) //在指定位置的前面插入新的元素
swap() //交换两个容器中的元素(相互替换)
insert(迭代器指定位置,新的元素) //在指定位置的前面插入新的元素(2)list --》链表,本质上是个链表
#include <list>
常用方法:
remove() //删除元素
remove_if() //带条件的删除,使用函数对象作为参数
sort() //两个版本,其中有一个版本也是使用函数对象作为参数(3)set --》集合,不允许存放重复元素,可以自动排序
#include <set>
常用方法:
count() //统计某个元素出现的次数
find() //查找某个元素(4)map --》存放键值对,用来存放数据之间的一一对应关系
#include <map>
键值对:表示数据的一一对应关系
键:星期一 张三
值:1 2017001
语法规则: map<键的类型,值的类型> mymap;
特点:存放的时候是无序的
键不能重复,值可以重复
比如: 星期一 1
星期二 2
张三 2017001
李四 2017002
(5)stack --》栈
#include <stack>
常用方法:
push() //压栈
pop() //删除栈顶元素
top() //返回栈顶元素(6)queue --》队列
#include <queue>
常用方法:
push() //入队
pop() //删除队首元素
front() //返回队首元素3.迭代器--》类似于指针
四种迭代器(适用于所有的容器)
第一种:读写迭代器--》既可以访问容器中的数据,也能修改容器中的数据
begin()和end()
注意:end返回的是容器最末尾后面一个位置
第二种:只读迭代器--》只能访问容器中的数据,不能修改容器中的数据
cbegin()和cend()
第三种:逆迭代器--》倒过来访问容器中的数据,能访问,能修改
rbegin()和rend()
第四种:只读逆迭代器--》倒过来访问容器中的数据,只能访问,不能修改
crbegin()和crend()4.新式for循环
for(auto &引用名字:容器对象)
{
//自动通过引用去遍历当前容器对象
}
#include<iostream>
#include<vector>
using namespace std;
int main()
{
//定义一个vector对象,用来存放整数
vector<int> myvector={111,222,333,444};
vector<int> othervector={456,789,123,741,852};
//赋值
//myvector.assign(8,666); //赋值8个666
//myvector.assign(othervector.begin(),othervector.end());
//返回最后一个元素
//cout<<"最后一个元素是: "<<myvector.back()<<endl;
//cout<<"容器的容量是: "<<myvector.capacity()<<endl;
//插入元素
//myvector.insert(myvector.begin()+1,555);
//交换两个容器中的内容
myvector.swap(othervector);
//othervector.swap(myvector);
//遍历容器,打印里面的数据
//写法一:传统的for循环
// int i;
// for(i=0; i<myvector.size(); i++)
// cout<<myvector.at(i)<<endl;
//写法二:使用迭代器来遍历
//定义一个迭代器
//vector<int>::iterator it;
//for(it=myvector.begin(); it!=myvector.end(); it++)
//cout<<*it<<endl;
//写法三:新式for循环
for(auto &x:myvector) //引用x自动遍历容器
cout<<x<<endl;
cout<<"================================="<<endl;
for(auto &x:othervector) //引用x自动遍历容器
cout<<x<<endl;
}
#include<iostream>
#include<vector>
using namespace std;
int main()
{
//定义一个vector对象,用来存放整数
vector<int> myvector;
//存放若干数据
myvector.push_back(55);
myvector.push_back(66);
myvector.push_back(77);
myvector.push_back(88);
//遍历容器,打印里面的数据
//第一种:读写迭代器--》既能访问数据也能修改数据
/* vector<int>::iterator it;
for(it=myvector.begin(); it!=myvector.end(); it++)
// cout<<*it<<endl; //访问数据
*it=*it+1; //修改数据
for(it=myvector.begin(); it!=myvector.end(); it++)
cout<<*it<<endl;
*/
//第二种:只读迭代器--》只能访问数据,不能修改数据
//auto it=myvector.cbegin();
//for(; it!=myvector.cend(); it++)
//cout<<*it<<endl; //访问数据
//*it=*it+1; //修改数据错误了,只读迭代器--》只能访问数据,不能修改数据
//第三种:逆迭代器
//auto it=myvector.rbegin();
//for(; it!=myvector.rend(); it++)
//cout<<*it<<endl;
//第四中:只读逆迭代器
auto it=myvector.crbegin();
for(; it!=myvector.crend(); it++)
cout<<*it<<endl;
//*it=*it+1; //修改数据错误了,只读逆迭代器--》只能访问数据,不能修改数据
}
函数符(函数对象)
1.定义
C++中函数对象(函数符): 指的是谓词函数,类重载圆括号,lambda表达式
函数对象这个概念从何而来??
类重载了圆括号,通过类的对象去调用重载圆括号的函数,这种写法既像构造对象,又像函数调用2.谓词函数
一元谓词函数: 返回值是bool类型,形参只有一个,这种类型的函数--》称之为一元谓词函数
二元谓词函数: 返回值是bool类型,形参有两个,这种类型的函数--》称之为二元谓词函数3.lambda表达式(也叫做匿名函数)
把bool返回值省略,函数名用中括号替代,参数,源码照抄
bool is_odd(int &x)
{
return x%2==1; ===>转换成lambda表达式 [](int &x){ return x%2==1; }
}
bool is_big(int &x,int &y)
{
return x>y; ===>转换成lambda表达式 [](int &x,int &y){ return x>y; }
}
类重载圆括号
#include <iostream>
using namespace std;
class Cat
{
public:
//重载圆括号
int operator()(int n)
{
cout<<"我无聊,重载了圆括号,参数是: "<<n<<endl;
}
};
int main()
{
//创建类的对象
Cat c1;
//调用重载的圆括号
//写法一:人类的思维习惯
c1(666); //看上去像是构造函数构造对象,但是实际是个函数调用
//写法二:函数调用
c1.operator()(999);
}
一元谓词函数
#include <iostream>
#include <list>
using namespace std;
//定义一个一元谓词函数
bool is_odd(int &n) //参数n会自动遍历容器mylist
{
cout<<"证明参数n确确实实是在自动遍历容器mylist "<<n<<endl;
if(n%2==1) //奇数
return true;
else //偶数
return false;
}
int main()
{
list<int> mylist;
mylist.push_back(854);
mylist.push_back(44);
mylist.push_back(13);
mylist.push_back(89);
mylist.push_back(68);
//删除所有的奇数
mylist.remove_if(is_odd);
//验证删除是否成功
for(auto &x:mylist)
cout<<"删除之后,mylist剩下: "<<x<<endl;
}
类重载圆括号
#include <iostream>
#include <list>
using namespace std;
//定义一个类,重载圆括号
class Test
{
public:
bool operator()(int &n) //n会自动遍历mylist
{
cout<<"证明n确确实实自动遍历mylist: "<<n<<endl;
if(n<20)
return true;
else
return false;
}
};
int main()
{
list<int> mylist;
mylist.push_back(854);
mylist.push_back(44);
mylist.push_back(13);
mylist.push_back(89);
mylist.push_back(68);
//删除所有<20的数
mylist.remove_if(Test());
//验证删除是否成功
for(auto &x:mylist)
cout<<"删除之后,mylist剩下: "<<x<<endl;
}
lambda表达式
#include <iostream>
#include <list>
using namespace std;
int main()
{
list<int> mylist;
mylist.push_back(854);
mylist.push_back(44);
mylist.push_back(13);
mylist.push_back(89);
mylist.push_back(68);
//删除所有的奇数
mylist.remove_if([](int &x){ return x%2==1; });
//验证删除是否成功
for(auto &x:mylist)
cout<<"删除之后,mylist剩下: "<<x<<endl;
}
STL中算法
1.算法的特点
STL中算法具有通用性:不属于任何一个容器类,但是所有的容器都能使用它们2.常用的算法
#include <algorithm> //所有的算法都是这个头文件
(1)遍历容器
for_each()
(2)查找
find()
find_if()
#include <iostream>
#include <algorithm> //算法对应的头文件
#include <vector>
using namespace std;
bool fun(int &x)
{
return x>=60;
}
int main()
{
vector<int> myvector={45,96,852,962,123,4};
//auto it=find(myvector.begin(),myvector.end(),4);
//if(it!=myvector.end())
//cout<<"找到了"<<endl;
//else
//cout<<"没有找到"<<endl;
//带条件的查找
auto it=find_if(myvector.begin(),myvector.end(),fun);
if(it!=myvector.end())
cout<<"找到了 "<<*it<<endl;
else
cout<<"没有找到"<<endl;
}
#include <iostream>
#include <algorithm> //算法对应的头文件
#include <vector>
using namespace std;
bool fun(int &x)
{
cout<<x<<endl;
return true;
}
class Test
{
public:
bool operator()(int &x)
{
cout<<x<<endl;
}
};
int main()
{
vector<int> myvector={45,96,852,962,123,4};
//for_each(myvector.begin(),myvector.end(),fun);
for_each(myvector.begin(),myvector.end(),Test());
}