STL概述 标准模板库

STL广义的三大组件 :容器、算法、迭代器

STL六大组件:容器、算法、迭代器、仿函数、适配器、空间配置器



算法
迭代器

迭代器的案例:

#include <iostream>
#include <vector>
using namespace std;
int main()
{
//单端动态数组 类模板
vector<int> v; //v是一个具体的vector容器
//push_back 尾部插入
v.push_back(1);
v.push_back(11);
v.push_back(111);
//访问数据
//定义一个迭代器 存储v的起始迭代器
vector<int>::iterator B_v = v.begin();
//定义一个迭代器 存储v的结束迭代器
vector<int>::iterator E_v = v.end();
//for循环遍历方式1
for(; B_v != E_v; B_v++){
//对迭代器取*代表容器元素
cout << *B_v << endl;
}
cout << endl;
//for循环遍历方式2 (推荐)
for(vector<int>::iterator p = v.begin(); p != v.end(); p++){
cout << *p << endl;
}
return 0;
}

案例 for_each
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
void fun(int v){
cout << v << " ";
}
int main()
{
//单端动态数组 类模板
vector<int> v; //v是一个具体的vector容器
//push_back 尾部插入
v.push_back(1);
v.push_back(11);
v.push_back(111);
//访问数据
//定义一个迭代器 存储v的起始迭代器
vector<int>::iterator B_v = v.begin();
//定义一个迭代器 存储v的结束迭代器
vector<int>::iterator E_v = v.end();
//for循环遍历方式1
for(; B_v != E_v; B_v++){
//对迭代器取*代表容器元素
cout << *B_v << endl;
}
cout << endl;
//for循环遍历方式2 (推荐)
for(vector<int>::iterator p = v.begin(); p != v.end(); p++){
cout << *p << endl;
}
cout << endl;
//STL提供的算法遍历 #include <algorithm>
//for_each 从容器的起始到结束 逐个元素取出并通过函数fun
for_each(v.begin(), v.end(), fun);
cout << endl;
return 0;
}


案例:容器存放自定义数据类型
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
class Person{
public:
string name;
int age;
Person(string name, int age): name(name), age(age){}
};
void fun(Person v){
cout << "name:" << v.name << " age:" << v.age << endl;
}
int main()
{
Person ob1("lucy1", 18);
Person ob2("lucy2", 28);
Person ob3("lucy3", 38);
//单端动态数组 类模板
vector<Person> v; //v是一个具体的vector容器
//push_back 尾部插入
v.push_back(ob1);
v.push_back(ob2);
v.push_back(ob3);
//STL提供的算法遍历 #include <algorithm>
//for_each 从容器的起始到结束 逐个元素取出并通过函数fun
for_each(v.begin(), v.end(), fun);
cout << endl;
return 0;
}

容器嵌套容器
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
void fun0(int in_vv);
void fun(vector<int> v){
for_each(v.begin(), v.end(),fun0);
cout << endl;
}
void fun0(int in_vv){
cout << in_vv << " ";
}
int main()
{
//单端动态数组 类模板
vector<int> v1; //v是一个具体的vector容器
vector<int> v2;
vector<int> v3;
//push_back 尾部插入
v1.push_back(1);
v1.push_back(11);
v1.push_back(111);
v2.push_back(2);
v2.push_back(22);
v2.push_back(222);
v3.push_back(3);
v3.push_back(33);
v3.push_back(333);
//定义一个容器v,存放v1,v2,v3
vector<vector<int>> v;
v.push_back(v1);
v.push_back(v2);
v.push_back(v3);
//for循环遍历
cout << "for循环遍历" << endl;
for(vector<vector<int>>::iterator p = v.begin(); p != v.end(); p++){
for(vector<int>::iterator in_p = (*p).begin(); in_p != (*p).end(); in_p++){
cout << *in_p << " ";
}
cout << endl;
}
//STL提供的算法遍历 #include <algorithm>
cout << "STL循环遍历" << endl;
//for_each 从容器的起始到结束 逐个元素取出并通过函数fun
for_each(v.begin(), v.end(), fun);
cout << endl;
return 0;
}

常用容器
string容器


vector容器 单端动态数组




容量>=元素的个数 原因:vector的未雨绸缪机制
vector另寻地址次数
#include <iostream>
#include <vector>
using namespace std;
int main()
{
vector<int> v;
int *p = NULL;
int count = 0;
for(int i=0; i<50; i++){
v.push_back(i);
if(p != &v[0]){
count ++;
p = &v[0];
}
}
cout << "另寻地址次数:" << count << endl;
return 0;
}

空间满后就需要另寻空间储存
vector的未雨绸缪机制

reserve空间预留


vector的常用操作
#include <iostream>
#include <vector>
using namespace std;
int main()
{
vector<int> v;
v.push_back(1);
v.push_back(11);
v.push_back(111);
//vector 的存取
//重载[]
cout << "重载[]" << endl;
cout << "v[0]: " << v[0] << ", v[1]: " << v[1] << ", v[2]: " << v[2] << endl;
// at下标
cout << ".at()" << endl;
cout << "v.at(0): " << v.at(0) << ", v.at(1): " << v.at(1) << ", v.at(2): " << v.at(2) << endl;
cout << endl;
/*[]和at的区别在于:
[]:发生越界时不抛出异常
at:发生越界时抛出异常
*/
//front()和back()
cout << "front()和back()" << endl;
cout << "v.front(): " << v.front() << endl;
cout << "v.back(): " << v.back() << endl;
cout << endl;
//vector的插入和删除
/*
insert(const_iterator pos, int count, ele); //迭代器指向pos插入count个ele
push_back(ele); //尾部插入元素ele
pop_back; //删除最后一个元素
erase(const_iterator start, const_iterator end); //删除迭代器从start到end
erase(const_iterator pos); //删除迭代器指向的元素
clear(); //删除容器中所有元素
*/
cout << "vector的插入和删除" << endl;
v.insert(v.begin()+1, 3, 0);
cout << "v.insert: ";
for(vector<int>::iterator p=v.begin(); p != v.end(); p++){
cout << *p << " ";
}
cout << endl;
cout << "pop_back: ";
v.pop_back();
for(vector<int>::iterator p=v.begin(); p != v.end(); p++){
cout << *p << " ";
}
cout << endl;
cout << "erase(v.begin()+1, v.end()-2): ";
v.erase(v.begin()+1, v.end()-2);
for(vector<int>::iterator p=v.begin(); p != v.end(); p++){
cout << *p << " ";
}
cout << endl;
cout << "erase(v.begin()+1): ";
v.erase(v.begin()+1);
for(vector<int>::iterator p=v.begin(); p != v.end(); p++){
cout << *p << " ";
}
cout << endl;
cout << "clear(): ";
v.clear();
for(vector<int>::iterator p=v.begin(); p != v.end(); p++){
cout << *p << " ";
}
cout << endl;
return 0;
}

deque容器 双端动态数组





API(接口)


#include <iostream>
#include <deque>
#include <algorithm>
using namespace std;
void PrintMem(int p){
cout << p << " ";
}
int main()
{
/*deque
##deque构造函数
deque<T> deqT; //默认构造形式
deque(beg, end); //构造函数将[beg, end)区间中的元素拷贝给本身
deque(n, elem); //构造函数将n个elem拷贝给本身
deque(const deque &deq); //拷贝构造函数
##deque赋值操作
assign(beg, end); //将[beg, end)区间中的数据拷贝给赋值本身
assign(n, elem); //将n个elem拷贝赋值给本身
deque& operator=(const deque &deq); //重载等号操作符
swap(deq); //将aeq与本身的元素互换
*/
deque<int> v0;
cout << "deque构造函数与赋值" << endl;
v0.assign(5, 2);
cout << "v0.assign(5, 2): ";
for_each(v0.begin(), v0.end(), PrintMem);
cout << endl;
deque<int> v1(v0.begin()+1, v0.end()-1);
cout << "deque v1(v0.begin()+1, v0.end()-1): ";
for_each(v1.begin(), v1.end(), PrintMem);
cout << endl;
deque<int> v2(5, 1);
cout << "deque v2(5, 1): ";
for_each(v2.begin(), v2.end(), PrintMem);
cout << endl;
deque<int> v3(v2);
cout << "v3(v2): ";
for_each(v3.begin(), v3.end(), PrintMem);
cout << endl;
deque<int> v4;
v4.assign(v3.begin(), v3.end());
cout << "v4.assign(v3.begin(), v3.end()): ";
for_each(v4.begin(), v4.end(), PrintMem);
cout << endl;
deque<int> v5;
v5 = v4;
cout << "v5 = v4: ";
for_each(v5.begin(), v5.end(), PrintMem);
cout << endl;
cout << "元素互换前" << endl;
cout << "v0: ";
for_each(v0.begin(), v0.end(), PrintMem);
cout << endl;
cout << "v5: ";
for_each(v5.begin(), v5.end(), PrintMem);
cout << endl;
cout << "元素互换后" << endl;
v0.swap(v5);
cout << "v0: ";
for_each(v0.begin(), v0.end(), PrintMem);
cout << endl;
cout << "v5: ";
for_each(v5.begin(), v5.end(), PrintMem);
cout << endl;
return 0;
}

案例:

#include <iostream>
#include <string.h>
#include <vector>
#include <algorithm>
using namespace std;
class Person{
friend Person WriteSore(Person &P);
public:
vector<string> name;
private:
vector<int> sore;
static void Printer_s(string p){
cout << p << " ";
}
static void Printer_i(int p){
cout << p << " ";
}
public:
void PrintMem(){
cout << "选手名字为: ";
for_each(name.begin(), name.end(), Printer_s);
cout << endl;
}
void PrintSore(int i, int num){
cout << "各项分数为: ";
for_each(sore.begin()+i*num, sore.begin()+i*num+num, Printer_i);
cout << endl;
}
void check(){
int mem = static_cast<int> (this->name.size());
int num = static_cast<int>((static_cast<int> ((this->sore).size()))/mem);
for(int i=0; i<mem; i++){
cout << *(name.begin()+i) << endl;
add(i, num);
}
}
void add(int i, int num){
int max = *(sore.begin()+i*num);
int min = *(sore.begin()+i*num);
int add_s = 0;
for(int j=0; j<num; j++){
add_s += *(sore.begin()+i*num+j);
max = max > *(sore.begin()+i*num+j)? max:*(sore.begin()+i*num+j);
min = min < *(sore.begin()+i*num+j)? min:*(sore.begin()+i*num+j);
}
cout << "总分: " << add_s << "; 平均分: " << add_s/num;
if(num <= 2){
cout << "; 无法计算中位平均分" << endl;
}
else{
cout << "; 中位平均分: " << (add_s-max-min)/(num-2) << endl;
}
}
};
Person WriteName(int num){
Person P;
for(int i=0; i<num; i++){
cout << "选手" << i+1 << "名称: ";
string name;
cin >> name;
P.name.push_back(name);
cout << "选手【" << *(P.name.end()-1) << "】已录入" << endl;
}
return P;
}
Person WriteSore(Person &P){
cout << "设置评委数量: ";
int num;
cin >> num;
for(int i=0; i<static_cast<int>(P.name.size()); i++){
cout << "选手" << i+1 << ": " << P.name[i] << endl;
for(int j=0; j<num; j++){
cout << "评委" << j+1 << "打分: ";
int s;
cin >> s;
if(s < 0){
cout << "你在干嘛?恶意评分!!";
break;
}
else{
P.sore.push_back(s);
cout << "分数" << s << "已录入" << endl;
}
}
P.PrintSore(i, num);
}
return P;
}
int main()
{
cout << "选手数量:";
int num;
cin >> num;
cout << endl;
cout << "名称录入" << endl;
Person P = WriteName(num);
cout << endl;
cout << "名称展示" << endl;
P.PrintMem();
cout << "成绩录入" << endl;
WriteSore(P);
cout << endl;
cout << "成绩检查" << endl;
P.check();
cout << endl;
return 0;
}

随机数


stack容器 栈容器(先进后出的数据结构)


queue容器 队列容器


list容器 链表容器




链表的API

list存放自定义数据 如果删除某个节点 必须重载==运算符
list存放自定义数据 如果删除某个节点 必须重载<运算符
list存放自定义数据排序。执行排序规则
指定排序规则 只需要指定交换的条件


使用仿函数


仿函数回顾

lambda表达式介绍

set/multiset容器


set的API






lower_bound upper_bound

equal_range


对组(pair)


仿函数修改set排序规则
#include <iostream>
#include <set>
#include <algorithm>
using namespace std;
class PX{
public:
bool operator()(int val1, int val2) const{
return val1 > val2;
}
};
int main()
{
//默认:小->大
/*更改排序规则
* set<int, 排序规则> P;
* 其中<>中应该放类型,而有一种既可以是类型又可以是函数的就是仿函数
*/
set<int, PX> P;
P.insert(1);
P.insert(4);
P.insert(2);
P.insert(5);
P.insert(3);
//打印 set的默认排序:从小到大
for_each(P.begin(), P.end(), [](int val){ cout << val << " ";});
cout << endl;
return 0;
}
自定义数据指定排序规则
#include <iostream>
#include <string.h>
#include <set>
#include <algorithm>
using namespace std;
class PX{
public:
string name;
int age;
public:
PX(string name, int age): name(name), age(age){}
};
class PP{
public:
bool operator()(const PX &ob1, const PX &ob2) const{
return ob1.age < ob2.age;
}
};
int main()
{
//默认:小->大
/*更改排序规则
* set<int, 排序规则> P;
* 其中<>中应该放类型,而有一种既可以是类型又可以是函数的就是仿函数
*/
set<PX, PP> P;
P.insert(PX("A", 1));
P.insert(PX("D", 4));
P.insert(PX("B", 2));
P.insert(PX("E", 5));
P.insert(PX("C", 3));
//打印 set的默认排序:从小到大
for_each(P.begin(), P.end(), [](PX val){ cout << val.name << " ";});
cout << endl;
return 0;
}
自定义数据重载<运算符
#include <iostream>
#include <string.h>
#include <set>
#include <algorithm>
using namespace std;
class PX{
public:
string name;
int age;
public:
PX(string name, int age): name(name), age(age){}
bool operator<(const PX &ob) const{
return this->age < ob.age;
}
};
int main()
{
//默认:小->大
/*更改排序规则
* set<int, 排序规则> P;
* 其中<>中应该放类型,而有一种既可以是类型又可以是函数的就是仿函数
*/
set<PX> P;
P.insert(PX("A", 1));
P.insert(PX("D", 4));
P.insert(PX("B", 2));
P.insert(PX("E", 5));
P.insert(PX("C", 3));
//打印 set的默认排序:从小到大
for_each(P.begin(), P.end(), [](PX val){ cout << val.name << " ";});
cout << endl;
return 0;
}
multiset 允许插入重复的键值
map容器



map的API

打印

find

map和vector配合使用
战队抽签
#include <iostream>
#include <map>
#include <vector>
#include <algorithm>
#include <numeric> //极少算法在其中调用 例如:random_shuffle(v.begin, v.end())
//种子头文件
#include <stdlib.h>
#include <time.h>
using namespace std;
int main()
{
//设置随机种子
srand(time(NULL));
//战队容器
map<int, string> M;
M.insert(make_pair(1, "RNG"));
M.insert(make_pair(2, "DWG"));
M.insert(make_pair(3, "EDG"));
M.insert(make_pair(4, "TSM"));
//战队编号容器
vector<int> v;
v.push_back(1);
v.push_back(2);
v.push_back(3);
v.push_back(4);
//随机洗牌,打乱容器中元素的顺序
random_shuffle(v.begin(), v.end());
//战队出场
for_each(v.begin(), v.end(), [&](int k){cout << "战队【" << //[&]可以调用外部数据
M[k] << "】出场"<< endl;});
cout << "Hello World!" << endl;
return 0;
}
multimap容器
multimap键值可以重复,map键值不允许重复
#include <iostream>
#include <map>
using namespace std;
int main()
{
map<int, string> m;
m.insert((make_pair(1, "RNG")));
m.insert((make_pair(1, "EDG")));
cout << m.count(1) << endl; //1
multimap<int, string> m1;
m1.insert((make_pair(1, "RNG")));
m1.insert((make_pair(1, "EDG")));
cout << m1.count(1) << endl; //2
return 0;
}

#include <iostream>
#include <map>
#include <vector>
using namespace std;
class Person{
public:
string name;
Person(string name): name(name){}
};
void creatP(vector<Person> &v){
v.push_back(Person("A"));
v.push_back(Person("B"));
v.push_back(Person("C"));
v.push_back(Person("D"));
v.push_back(Person("E"));
}
void join(vector<Person> &v, multimap<int, Person> &m){
for(vector<Person>::iterator i=v.begin(); i != v.end(); i++){
cout << "员工" << (*i).name << "加入部门(可选:1、2、3):" << endl;
int delect = 0;
cin >> delect;
if(delect > 0 && delect < 4){
m.insert(make_pair(delect, *i));
}
else{
cout << "违规部门" << endl;
}
}
}
void print(multimap<int, Person>::const_iterator v, int num);
void show(multimap<int, Person> &m, int a){
switch(a){
case 1:
cout << "------------" << endl;
cout << "部门" << a << "共" << m.count(a) << "人" << endl;
print(m.find(a), m.count(a));
break;
case 2:
cout << "------------" << endl;
cout << "部门" << a << "共" << m.count(a) << "人" << endl;
print(m.find(a), m.count(a));
break;
case 3:
cout << "------------" << endl;
cout << "部门" << a << "共" << m.count(a) << "人" << endl;
print(m.find(a), m.count(a));
break;
}
}
void print(multimap<int, Person>::const_iterator v, int num){
for(int i=0; i<num; i++, v++){
// cout << num << endl;
// cout << i << endl;
cout << "姓名:" << (*v).second.name << endl;
}
}
int main()
{
vector<Person> v;
//创建员工
creatP(v);
multimap<int, Person> m;
//加入部门
join(v, m);
//查看部门情况
show(m, 1);
show(m, 2);
show(m, 3);
return 0;
}


算法

谓词 返回值为bool类型的普通函数或函数对象

一元谓词 (案例:寻找)
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
//普通函数
bool than2(int val){
return val>2;
}
//仿函数
class Than2{
public:
bool operator()(int val){
return val>2;
}
};
int main()
{
vector<int> v;
v.push_back(1);
v.push_back(2);
v.push_back(3);
v.push_back(4);
//普通函数 一元谓词
vector<int>::iterator i0;
i0 = find_if(v.begin(), v.end(), than2);
if(i0 != v.end()){
cout << "找到第一个大于2的数为:" << *i0 << endl;
}
else{
cout << "未找到" << endl;
}
//仿函数 一元谓词
vector<int>::iterator i1;
i1 = find_if(v.begin(), v.end(), Than2());
if(i1 != v.end()){
cout << "找到第一个大于2的数为:" << *i1 << endl;
}
else{
cout << "未找到" << endl;
}
return 0;
}
二元谓词(案例:比较)
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
//普通函数
bool px(int val0, int val1){
return val0>val1;
}
//仿函数
class PX{
public:
bool operator()(int val0, int val1){
return val0<val1;
}
};
int main()
{
vector<int> v;
v.push_back(1);
v.push_back(2);
v.push_back(3);
v.push_back(4);
for_each(v.begin(), v.end(), [](int val){cout << val << " ";});
cout << endl;
//普通函数 二元谓词
sort(v.begin(), v.end(), px);
for_each(v.begin(), v.end(), [](int val){cout << val << " ";});
cout << endl;
//仿函数 二元谓词
sort(v.begin(), v.end(), PX());
for_each(v.begin(), v.end(), [](int val){cout << val << " ";});
cout << endl;
return 0;
}

内建函数对象





适配器 扩展函数的参数接口

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
//仿函数
class Than: public binary_function<int, int, bool>{
public:
bool operator()(int val, int c) const {
return val>c;
}
};
int main()
{
vector<int> v;
v.push_back(1);
v.push_back(2);
v.push_back(3);
v.push_back(4);
vector<int>::iterator i0;
//适配器
/*1、使用bind1st或bind2nd适配绑定参数
*2、适配器中的函数必须是class类型的函数(也就是仿函数)
*3、仿函数必须公共继承二元函数适配器class Than: public binary_function
*4、参数萃取class Than: public binary_function<输入参数1类型, 输入参数2类型, 返回值类型>
*5、const修饰仿函数bool operator()(int val, int c) const {}
*/
i0 = find_if(v.begin(), v.end(), bind2nd(Than(), 2));
if(i0 != v.end()){
cout << "找到第一个大于2的数为:" << *i0 << endl;
}
else{
cout << "未找到" << endl;
}
return 0;
}
bind2nd和bind1st的区别
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
class C: public binary_function<int, int, void>{
public:
void operator()(int val0, int val1) const {
cout << "第一参数val0:" << val0 << " 第二参数val1:" << val1 << endl;
}
};
int main()
{
vector<int> v;
v.push_back(1);
v.push_back(2);
v.push_back(3);
v.push_back(4);
cout << "-----bind1st-----" << endl;
for_each(v.begin(), v.end(), bind1st(C(),2));
cout << "-----bind12nd-----" << endl;
for_each(v.begin(), v.end(), bind2nd(C(),2));
return 0;
}


取反适配器
一元取反适配器
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
class great3: public unary_function<int, bool>{
public:
bool operator()(int val) const{
return val>3;
}
};
int main()
{
vector<int> v;
v.push_back(1);
v.push_back(2);
v.push_back(3);
v.push_back(4);
v.push_back(5);
cout << "找出第一个大于3的数" << endl;
vector<int>::iterator ret0;
ret0 = find_if(v.begin(), v.end(), great3());
cout << *ret0 << endl;
cout << endl;
cout << "取反适配器" << endl;
/*一元取反适配器
* 1、使用not1取反适配器 修饰取反的仿函数
* 2、继承一元函数public unary_function
* 3、参数萃取
* 4、const修饰
*/
cout << "找出第一个小于3的数" << endl;
vector<int>::iterator ret1;
ret1 = find_if(v.begin(), v.end(), not1(great3()));
cout << *ret1 << endl;
return 0;
}

总结: binary_function 二元继承 unary_function 一元继承
二元取反适配器
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
class G: public binary_function<int, int, bool>{
public:
bool operator()(int val0, int val1) const{
return val0 < val1;
}
};
class S{
public:
bool operator()(int val0, int val1){
return val0 < val1;
}
};
int main()
{
vector<int> v;
v.push_back(2);
v.push_back(1);
v.push_back(4);
v.push_back(3);
cout << "默认sort从小到大排序" << endl;
sort(v.begin(), v.end());
for_each(v.begin(), v.end(), [](int val){cout << val << " ";});
cout << endl;
cout << "使用greater内建函数从大到小排序" << endl;
sort(v.begin(), v.end(), greater<int>());
for_each(v.begin(), v.end(), [](int val){cout << val << " ";});
cout << endl;
cout << "使用仿函数从小到大排序" << endl;
sort(v.begin(), v.end(), S());
for_each(v.begin(), v.end(), [](int val){cout << val << " ";});
cout << endl;
cout << "使用not2二元取反 从大到小排序" << endl;
sort(v.begin(), v.end(), not2(G()));
for_each(v.begin(), v.end(), [](int val){cout << val << " ";});
cout << endl;
cout << "使用内建函数取反 从小到大" << endl;
sort(v.begin(), v.end(), not2(greater<int>()));
for_each(v.begin(), v.end(), [](int val){cout << val << " ";});
cout << endl;
return 0;
}

成员函数适配器
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
class Person{
public:
string name;
int age;
public:
Person(string name, int age): name(name), age(age){}
void show(){
cout << "名字:" << name << " 年龄:" << age << endl;
}
};
void SHow(Person &ob){
cout << "名字:" << ob.name << " 年龄:" << ob.age << endl;
}
int main()
{
vector<Person> v;
v.push_back(Person("A", 1));
v.push_back(Person("B", 2));
v.push_back(Person("C", 3));
v.push_back(Person("D", 4));
cout << "普通函数遍历" << endl;
for_each(v.begin(), v.end(), SHow);
cout << endl;
cout << "使用函数适配器mem_fun_ref 成员函数遍历" << endl;
for_each(v.begin(), v.end(), mem_fun_ref(&Person::show));
cout << endl;
return 0;
}

总结:

函数指针适配器(普通函数作为适配器)
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
void add(int val, int t){
cout << val+t << " ";
}
int main()
{
vector<int> v;
v.push_back(1);
v.push_back(2);
v.push_back(3);
/*通常情况下bind2nd中函数应该是仿函数,普通函数是无法识别的
* 可以通过ptr_fun将普通函数作为函数适配器
*/
for_each(v.begin(), v.end(), bind2nd(ptr_fun(add), 10));
cout << endl;
return 0;
}


常用的遍历算法
for_each

transform算法

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
int swapp(int val){
return val;
}
int main()
{
vector<int> v;
v.push_back(1);
v.push_back(2);
v.push_back(3);
//待搬运容器vv
vector<int> vv;
//设置vv大小
vv.resize(v.size());
//transform搬运
//transform(v.begin(), v.end(), v.begin(), 搬运方式)
transform(v.begin(), v.end(), vv.begin(), swapp);
for_each(vv.begin(), vv.end(), [](int val){cout << val << " ";});
cout << endl;
return 0;
}

常用的查找算法
find

find_if

adjacent_find
binary_search 二分法查找(容器必须有序)


常用排序算法

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
int swapp(int val){
return val;
}
int main()
{
vector<int> v0;
v0.push_back(1);
v0.push_back(3);
v0.push_back(5);
for_each(v0.begin(), v0.end(), [](int val){cout<<val<<" ";});
cout << endl;
vector<int> v1;
v1.push_back(2);
v1.push_back(4);
v1.push_back(6);
for_each(v1.begin(), v1.end(), [](int val){cout<<val<<" ";});
cout << endl;
vector<int> v;
v.resize(v0.size()+v1.size());
merge(v0.begin(), v0.end(), v1.begin(), v1.end(), v.begin());
for_each(v.begin(), v.end(), [](int val){cout<<val<<" ";});
cout << endl;
return 0;
}

sort算法

random_shuffle算法

常用拷贝和替换算法





相同类型的两个容器交换swap
算数生成算法



常用集合算法




结果:7 9


set_difference 求差集

STL案例


#include <iostream>
#include <vector>
#include <map>
#include <algorithm>
#include <stdlib.h>
#include <time.h>
using namespace std;
class Person{
public:
char name;
vector<int> score;
int num;
public:
Person(char name, int num): name(name), num(num){}
void pick(int v){
score.push_back(v);
}
};
void Print(map<int, Person> &ob){
for_each(ob.begin(), ob.end(), [](pair<int, Person> v){
cout << "编号:" << v.first << " 名字:" << v.second.name << endl;
});
}
void Print(multimap<int, Person, std::greater<int>> &ob){
for_each(ob.begin(), ob.end(), [](pair<int, Person> v){
cout << "得分:" << v.first << " 名字:" << v.second.name << " 编号:" << v.second.num <<endl;
});
}
void GetPerson(map<int, Person> &ob){
int j = 65;
int i =100;
for(;i<124;i++, j++){
char t = char(j);
ob.insert(make_pair(i, Person(t, i)));
}
}
vector<int> Race(vector<int> &z, map<int, Person> &m){
vector<int> people;
int i = z.size()/6;
for(int j=0; j<i; j++){
cout << "第" << j+1 <<"组出场" << endl;
multimap<int, Person, std::greater<int>> mu;
for(int jj=0; jj<6; jj++){
int p = *(z.begin()+j*6+jj);
cout << "编号:" << p << " 名字:" << m.find(p)->second.name;
cout << " 打分:";
int s = rand()%99 + 1;
m.find(p)->second.pick(s);
cout << *(m.find(p)->second.score.end()-1) << endl;
//得分装入multimap容器排序 得分可能重复
mu.insert(make_pair(s, m.find(p)->second));
}
cout << "第" << j+1 <<"组得分排序" << endl;
Print(mu);
cout << "第" << j+1 <<"组晋级名单" << endl;
multimap<int, Person, std::greater<int>>::const_iterator it = mu.begin();
people.push_back((*it).second.num);
it++;
people.push_back((*it).second.num);
it++;
people.push_back((*it).second.num);
for_each(people.begin()+j*3, people.end(), [&](int v){
cout << "编号:" << v << " 姓名:" <<
(*(m.find(v))).second.name <<
" 得分:" << *(m.find(v)->second.score.end()-1) <<endl;
});
}
cout << "晋级总人数:" << people.size() << endl;
return people;
}
int main()
{
cout << "参赛成员录入" << endl;
map<int, Person> m;
GetPerson(m);
Print(m);
//创建抽签编号
vector<int> z;
int i =100;
for(;i<124;i++){
z.push_back(i);
}
//设置随机种子
srand(time(NULL));
cout << "-----随机分组1-----" << endl;
random_shuffle(z.begin(), z.end());
cout << "比赛1" << endl;
//晋级人员
vector<int> p1;
p1 = Race(z, m);
cout << "------随机分组2------" << endl;
random_shuffle(p1.begin(), p1.end());
cout << "比赛2" << endl;
//晋级人员
vector<int> p2;
p2 = Race(p1, m);
cout << "------随机分组3------" << endl;
random_shuffle(p2.begin(), p2.end());
cout << "比赛2" << endl;
//晋级人员
vector<int> p3;
p3 = Race(p2, m);
cout << "------最终成绩展示------" << endl;
for_each(p3.begin(), p3.end(), [&](int v){
cout << "编号:" << v << " 姓名:" <<
(*(m.find(v))).second.name <<
" 得分1:" << *(m.find(v)->second.score.begin()) <<
" 得分2:" << *(m.find(v)->second.score.begin()+1) <<
" 得分3:" << *(m.find(v)->second.score.begin()+2) << endl;
});
return 0;
}
注:仅学习总结

578

被折叠的 条评论
为什么被折叠?



