std::function std::bind
我们知道在C里面有函数指针这么回事,我们用函数指针的目的就是将仿函数作为参数,传递给另外一个函数,并供他调用。但是显然,函数指针那种写法还是相当恶心的,比如:
1 |
|
而C++11里提供了std::function这个工具来封装函数指针,上面的写法就可以变成下面的:
1 |
|
用函数模板来体现作为参数的函数类型,看起来更优雅方便。
但是有时候,我们可能希望这个function能够绑定一些参数,那么就需要用到std::bind这个工具来封装旧的function,并返回新的function:
1 |
|
上面的意思是将int(int,int)这个函数封装成了int(10,int)这个函数并起名为binded,std::placeholders::_1表示的就是在调用时传入的第一个参数(这里是3)。非常好理解。
使用std::function和std::bind可以非常装逼的组合多个函数,非常具有模块化的思想,比如下面的函数:
1 |
|
其实就是实现了统计[low,high]之间的数字个数的功能。。。
lambda表达式
lambda表达式我认为说白了就是一种匿名函数的简写形式,是一种仿函数的语法糖,可以看成是一个std::function对象,没什么稀奇的。
基本写法
基本写法如下:
1 | [capture] (params) opt -> ret {body;}; |
比如下面的函数fun1、fun2就是等价的:
1 | int callback(int x,int y){ |
捕获外部变量
为了保证良好的封装性,lambda并不能随意访问非参数外的其他变量,这些变量的访问权限交由[]
来控制,具体用法如下:
[]
不捕获任何变量[&]
按引用捕获所有变量[=]
按值捕获所有变量[=,&foo]
按值捕获所有变量,并按引用捕获foo变量[foo]
按值捕获foo变量,不捕获其他变量[this]
捕获当前类中的this指针
比如下面的例子就是按值捕获了外部变量x,如果使用[]
,那么编译会报错。
1 |
|
需要注意的是,捕获的过程是在函数定义的时候就发生的,在捕获时就会复制一个新的变量,因此我们注意到下面的例子:
1 |
|
如果我们需要即时的捕获外部变量,我们就需要按引用捕获。
mutable选项
由于C++的规定,lambda表达式的operator()是const的,也就是说我们按值捕获的值默认是const的,因此我们对按值捕获的值是无法修改的,这就很蛋疼了?这时候就用到了mutable选项来取消const的限制了:
1 |
|
简单应用
有了lambda函数,很多事情就变的简单了,比如之前的统计一定范围内数字个数的程序就可以修改成下面这样:
1 |
|
tuple元组
没想到C++里面竟然也有元组,元组这个东西其实就是一个简化的结构体,方便我们将不同的数据进行打包,跟python中的用法类似:
创建元组
1 |
|
两种方法,一种是构造函数,一种是make_tuple函数。
提取元素
1 |
|
两种方法,一种是get函数,可以指定提取的元素位置,另一种是std::tie方法,可以一次提取所有的元素也可以提取某一个元素,其他位置用std::ignore占位。
如果忘记了tuple的大小,我们可以使用tuple_size来获得tuple的大小:
1 |
|
元组连接
1 |
|
通过tuple_cat来连接两个tuple。