STL的泛型算法使用详解

前言


c++文章连载:
1.C++基础
  1.C++基础
  2.C++新增和有变化的关键字
  3.C++的内存管理
2.面向对象
  1.C++的封装和访问权限
  2.C++继承和多态特性
  3.C++的运算符重载
  4.C++静态类和静态成员
  5.C++的友元函数和友元类
3.模板编程和STL
  1.C++模板编程入门
  2.STL的容器类和迭代器
  3.STL的泛型算法
  4.模板特化与类型萃取
  5.STL的其他容器讲解
  6.智能指针与STL查漏补缺
4.杂项
  1.c++各种流操作
  2.依赖,关联,聚合,组合,继承
  3.一些技巧性的代码设计
  
  


1.什么是泛型算法

1.1、从容器说起
(1)容器是数据结构,是对数据的封装
(2)各容器都提供了少量处理元素操作的方法,譬如sort,但没有提供更多
(3)同样的操作譬如sort,在不同容器中底层处理肯定会不同
(4)泛型算法是独立于容器类的一些操作方法,可以用于多种容器,所以叫“泛型”算法
(5)泛型算法实际上是更高层次的抽象,所以设计和实现的难度很大,这也是STL的核心技术
1.2、泛型算法使用基础
(1)泛型算法参考:https://zh.cppreference.com/w/cpp/algorithm
(2)泛型算法所在头文件

2.泛型算法使用实战

2.1、泛型算法和容器迭代器的适配
(1)算法中对迭代器有要求
(2)容器中包含的迭代器有特性
(3)2者兼容才可结合使用,否则不可使用
1.3、泛型算法使用举例
(1)使用sort为array默认排序
(2)使用sort为list默认排序
(3)使用sort为list由大到小排序

3.谓词predicate和函数对象引入

3.1、何为谓词
(1)谓词就是可以做谓语的词,就是“动词、动作”性质语义的词
(2)C/C++中的函数function就是典型的谓词语义
(3)C++ STL中的谓词类似这样:bool func(T& a); 或者 bool func(T&a, T& b);
(4)常见的谓词:函数,函数指针,lambda表达式,函数对象,库定义的函数对象
3.2、函数对象引入
(1)函数对象 function object, 也叫仿函数 functor
(2)函数对象在语法上不是函数,而是个类
(3)函数对象在调用形式上看起来像个函数
3.3、函数对象案例实践
(1)写一个函数,判断传参是否大于0
(2)用函数对象实现,对比、分析、体会

4_5.函数对象的一些细节1_2

4.1、STL中定义的函数对象的分析
4.2、自定义函数对象用于STL算法库
4.3、函数对象的优势
(1)函数对象可以使用template技术实现多类型支持,这比函数的重载技术更有优势
(2)函数对象可以有自己的状态。我们可以在类中定义状态变量(类私有成员变量),这样一个函数对象在多次的调用中可以共享这个状态。参考:https://www.cnblogs.com/gis-user/p/5086218.html
(1)函数对象有自己的状态,即它可以携带自己的成员函数,而且这个函数对象在多次调用的过程中它的那些状态是共享的,而函数则不能做到这点(除非定义函数内部的静态变量或者全局变量)。
(2)函数对象有自己的类型,而普通函数则没有。在使用STL的容器时可以将函数对象的类型传递给容器作为参数来实例化相应的模板,从而来定制自己的算法,如排序算法。

6.STL典型泛型算法解读1

7.STL典型泛型算法解读2

8.CPP之lamba表达式

8.1、实践体会lamba表达式
(1)lambda表达式使用举例:上节all_of示例代码
(2)使用函数对象实现类似于lambda表达式的效果
8.2、lambda表达式总结
(1)lambda表达式 就是一个匿名函数,相当于一次使用的、直接原地展开调用的函数
(2)lambda表达式也叫闭包,就是在别的地方无法调用的封包
(3)lambda表达式其实就是一个函数对象,在内部创建了一个重载()操作符的类
8.3、lambda表达式格式
(1)完整格式5部分:[参数捕获] (操作符重载函数参数) mutable或exception声明 ->返回值类型 {函数体}
(2)最简单的lambda表达式:{},调用执行时为{}();
(3)带传参的lambda表达式:[](int i){//i在这里可以用}
(4)使用auto将lambda表达式定义为一个变量,再以变量方式调用
(5)使用->int这种方式让lambda表达式函数返回相应类型的值

9.lambda表达式之参数捕获

9.1、什么是参数捕获
(1)实验:在lambda表达式外面定义int a,在表达式内部试图访问
(2)解决:在[]中增加捕获说明即可
(3)总结:所谓参数捕获,就是让lambda表达式内部可以捕获并使用外部的变量
9.2、lambda表达式的捕获列表
(1)[] 空,完全不捕获
(2)[=] 等号,以值传参方式捕获,捕获范围是表达式所在作用范围(包括所在类的this),会把不是const的变量变成const类型的,因为值传递,a真身是不进入lambda中的,所以改不了a的值,那么编译器干脆把他变成const类型。
(3)[&] &号,以引用传参方式捕获,捕获范围是表达式所在作用范围(包括所在类的this)
(4)[this] 只捕获lambda表达式所在类的this可访问的那些
(5)[a] 仅以值方式捕获a,其他全部不捕获
(6)[&a] 仅以引用方式捕获a,其他全部不捕获
(7)[a, &b] 仅以值方式捕获a,以引用方式捕获b,其余完全不捕获
(8)[=, &a, &b] 仅以引用方式捕获a和b,其余以值方式捕获
(9)[&, a, b] 仅以值方式捕获a和b,其余以引用方式捕获
9.3、lambda表达式总结
(1)lambda表达式提供一种单次使用的函数简写方式
(2)通过捕获列表,在lambda表达式内部也可以访问外部的变量,相当于函数传参

10.CPP函数适配器

10.1、什么是函数适配器
(1)适配器,adapter,用来在不适配的2端间对接的连接器
(2)函数适配器是在不同传参个数的函数间进行适配的技术
(3)几个概念:1元函数、2元函数、1元谓词、2元谓词
10.2、C++的函数适配器
(1)早期C++98时,常用bind1st bind2nd
(2)C++11开始,引入加强版:std::bind
10.3、bind的学习
参考:https://blog.csdn.net/u013654125/article/details/100140328

11.STL典型泛型算法解读3

for_each和transform

12.STL典型泛型算法解读4

12.1、再看几个泛型算法
12.2、泛型算法总结
(1)理解谓词和函数对象,是学习和使用泛型算法的基础
(2)泛型算法很多,但是套路是类似的,学会的关键是理解并会用这种套路
(3)不建议试图死记硬背所有泛型算法,建议实战中去熟悉、去用起来并记住
(4)能用现成泛型算法写代码就不要自己造轮子
(5)一个潜在问题警告:C++包的越来越多,不要想当然,未经验证确认的代码都要有怀疑精神

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值