以商品举例,可以通过名字 排序,可以通过价格排序,可以通过评价排序
在C++中,使用仿函数可以进行 价格的比较 若不看仿函数具体实现,则无法通过仿函数对象 来知道 该仿函数到底是怎么比较的 所以就提出了lambda表达式
1.[capture-list] :捕捉列表
该列表出现在lambda的开始位置 捕捉列表可以捕捉上下文变量供 lambda函数使用 不可省略,若不进行任何捕捉,则写成 []
2.(paraments) :参数列表
与函数的参数列表相同 若没有参数,可以将()省略
3.mutable:异变
(后面会详细说)
4.-> return- type :返回值类型
可省略,编译器会对返回类型进行推导
5.{statement} :函数体
在函数体内部,除了使用其参数外,还可用捕捉的变量
捕捉列表:不可省略,若不进行任何捕捉,则写成 [] 参数列表:存在两个参数 x 和 y 异变:不使用时,可省略 返回值类型:是可以省略的,编译器会自动推导 (但一般不建议省略) 函数体:要注意内部是要有分号的,代表语句结束
表达式整体代表一个lambda对象,是可以被调用的
将返回值类型省略,编译器可以自动推导
通过lambda表达式 即可清楚了解 lambda表达式对象内部如何实现比较的
若想修改升序或降序,只需修改对应的lambda表达式代码即可
若不进行任何捕捉,使用lambda表达式完成交换
若想用外面域的变量,则需要捕捉, 捕捉多个值,用逗号分割
由于是传值捕捉,所以捕捉过来的a和b是外面的拷贝,是无法改变的
加入mutable 异变
,即可修改传值捕捉所过来的a和b 但是无法完成交换,传值捕捉所进行的修改,并不会影响 本身
使用引用的方式,即可通过修改捕捉后的a和b,来影响本身 的值进行修改
a引用捕捉,b传值捕捉
假设有一堆的变量,不想一个一个捕捉 使用 [&] 即全部使用引用捕捉
使用 [=] 即全部使用传值捕捉
除了a使用传值捕捉以外,其他全部使用引用捕捉
pthread库是 POSIX线程库,POISIX(可移植操作系统接口) windows 与linux 下的库是不一样的
C++11中,linux和windows下都支持多线程程序 即 使用 thread库
第一个参数 作为模板类型,所以可以是 函数指针 、仿函数对象 或 lambda对象 为可调用的对象即可
对于第二个参数 Args&&....args来说 通过模板的可变参数,想传几个参数都可以 使用万能引用,当为左值时,发生引用折叠,即可以看作是& ,调用深拷贝 当为右值时,发生移动构造,进行资源转移
对于thread库的调用,与linux中的pthread库大部分功能都是类似的, 如:join 与 pthread_jojn 功能相同 ,线程等待 若一个新线程被创建出来,需要主线程就等待的 detach 与pthread_detach 功能相同,线程分离 默认是阻塞的 ,即主线程等待 新线程退出,主线程 想做其他事情
使用lambda对象 作为可被调用对象 通过lambda表达式对象, 先将 a进行传值捕捉,将1作为sum ,再进行循环 再将 b进行传值捕捉,将2作为sum,再进行循环
允许移动赋值
每次都创建一个线程,其整体可以看作是一个匿名对象,属于右值,所以进行移动赋值 将新建线程的资源转移到线程数组中
实际上是1字节
编译器会把lambda处理成仿函数
先查看仿函数的汇编
先调用构造函数,使r1成为仿函数对象 再调用rate类中的operator()
再查看lambda的汇编
由编译器生成一个不重复的类,(保证每个lambda都不一样),用该类调用构造函数 以及 调用类中的 operator()
仿函数汇编的调用与lambda汇编的调用都是先调用构造函数,在调用operator(),说明lambda底层就为仿函数实现的
根据仿函数,生成仿函数的类,由于仿函数的类是空类 ,所以为1字节 即lambda对象为1字节