【C++11】 包装器 | bind

2023-10-17 09:04:20 浏览数 (2)

1. 包装器

概念理解

function包装器 也被叫做 适配器 C 11中function本质是类模板,也是一个包装器

意义在于 对可调用对象类型进行封装再适配

可调用对象:函数指针 / lambda / 仿函数


用法

需要包含 头文件 functional

模板参数 Ret : 被调用函数的返回类型 ...Args作为参数包,这个参数包中包含0到任意个模板参数 Args... :被调用函数的形参


f作为函数指针,Functor作为一个类 ,两者类型是完全不同的, 想要声明出统一的类型,就需要借助包装器进行包装,从而适配出统一的可调用对象的类型

function<int(int,int)> 第一个int作为返回值 小括号中的两个int参数,作为被调用函数的参数 此时既可以使用函数指针进行初始化,也可以使用仿函数进行初始化


对于产生的包装器对象v1和v2,两者的类型是相同 但在调用时,一个调用的是f函数,一个调用的是Functor中的operator()


包装器作为map的第二个参数 包装器的返回值为int类型,被调用函数有两个int的参数 可以将 f (函数指针) 、 Functor (仿函数)、 lambda表达式 作为可调用对象 传给包装器 ,对包装器进行初始化

成员函数的包装

成员函数中分为静态成员函数和非静态成员函数

静态成员函数

对于静态成员函数,可以直接使用包装器 function 通过Plus这个类去寻找到plusi 这个函数 ,对包装器 进行初始化即可

非静态成员函数

对于普通成员函数,是没办法直接使用 function包装器的 普通成员函数在类中有 this指针存在, 所以要在main函数中要加入 Plus


这里不是直接去调用plusd这个函数的, 而是通过Plus对象去调用 plusd


这里不是直接去调用plusd这个函数的, 而是通过指针去调用 plusd 若为plus*,则匿名对象是需要取地址的 而匿名对象属于右值,不能取地址 , 所以使用Plus*,不能使用匿名对象


最后加入&后, 即可解决 问题 (加&是规定)

2. bind

概念理解

bind函数 定义在头文件中,是一个函数模板

bind函数可以看作一个通用的函数适配器,它接受一个可调用对象(函数指针 仿函数 lambda对象) 生成一个新的可调用对象来 适应 原对象的参数列表


调用bind的一般形式:auto newCallable = bind(callable,arg_list);

arg_list中的参数可能包含形如_n的名字,其中n是一个整数,这些参数是占位符, _1表示第一个参数,_2表示第二个参数 ,但默认情况下获取不到 (_1 和_2被放到命名空间中)

绑定的参数被放到 placeholders 中


placeholders 命名空间中,有_1 _2 _3等 符号存在 所以想使用_1表示第一个参数 ,需在placeholders命名空间中访问_1 即 placehlders::_1

功能1 调整参数顺序 (用处不大)

正常情况下,把1传给参数a,把2传给参数b ,打印a=1 b=2


若想把1传给参数b,把2传给参数a ,则使用bind

bind的第一个参数为可调用对象 bind的参数包作为占位符,借助placeholders 命名空间 来访问里面的字符(_1 _2)

把Sub1函数中的第二个参数2传给Sub函数的a 把Sub1函数中的第一个参数1传给Sub函数的b

绑定后 会返回一个可调用对象, 可以选择使用auto 自动推导类型 再通过返回的对象,再次调用1 2 ,则结果不同


功能2 调整参数个数

在Sub类中的 func函数,虽然看似只有两个参数,但是还有一个隐藏的this指针存在


若使用包装器,则需三个参数,通过匿名对象去调用func函数


function中的参数个数与 func的参数个数 不同 若想两者参数个数相同,则需要绑定,进行调整参数的个数

bind可以把某个参数绑死 (把其中一个参数显示传过去)

把匿名对象显示传过去,此时匿名对象就绑死了 placehlders::_1和 placehlders::_2 表示剩下的两个参数 可调用对象 只需 传递两个参数 即可

0 人点赞