113 C++ STL 适配器 bind1st, bind2nd,bind,reverse_iterator

本文详细介绍了适配器在C++中的三种类型:容器适配器(如stack和queue)、算法适配器(如bind函数及其变体)以及迭代器适配器(如reverse_iterator)。重点讲解了bind函数在函数对象和算法中的应用,展示了如何通过适配器灵活处理不同场景的需求。
摘要由CSDN通过智能技术生成

一 适配器基本概念

把一个既有的东西,进行适当的改造,比如增加点东西,或者减少点东西,就构成了一个适配器。

三种适配器:容器适配器,算法适配器,迭代器适配器

二 容器适配器

stack 和 queue

在前面学过的deque,stack 和 queue可以看成是deque的阉割版。

把一个既有的deque,减少点东西,就构成了一个适配器,从这个层面来说,stack 和 queue又变成适配器了。

三 算法适配器(也叫函数适配器)

最典型的就是绑定器

绑定器

老版本中 绑定器 bind1st, bind2nd;C++11之前

在C++11后,叫做bind 

bind 的用法和解析,

class Teacher8 {
public:
	bool operator()(int value1) {
		return value1 > 68;
	}
};
void main() {
	//bind 使用举例,在C++11之前叫做bind1st, bind2nd
	vector<int> vec = { 68,98,23456,68,68,93569,89898 };
	//我们目前是想要统计等于68的个数
	int num = count(vec.begin(), vec.end(), 68);
	cout << "68的个数为:" << num << endl;

	//我们目前是想要统计>68的个数,自己写一个函数对象实现
	num = count_if(vec.begin(), vec.end(), Teacher8());
	cout << "dayu 68的个数为:" << num << endl;

	//我们目前是想要统计>68的个数,想要用C++提供了函数对象实现。
	//查了一下,发现,好像没有一个和具体值比较的。
	//就这个 greater<type>()比较接近,但是传递的是两个参数,一个是vec.begin()的值,一个是vec.end()的值
	//这时候就要用到bind 将 greater<int>的一个参数绑定,那么绑定哪一个呢?
	//这时候就要查看一下 greater<int> 中的operator()方法的实现了,如下:
			//constexpr bool operator()(const _Ty& _Left, const _Ty& _Right) const
			//{	// apply operator> to operands
			//	return (_Left > _Right);
			//}
	//我们发现,返回值是 left> right,也就是如果我们要统计 大于 68的,那么第二个参数就应该是68


	auto aa= bind(greater<int>(),placeholders::_1,68);//就像这样,那么 placeholders::_1怎么理解呢?表示该 适配器调用时 传进去的第一个参数
	bool res = aa(90);//因为90 > 68 的,因此res的值是1
	cout << "res = " << res << endl;
	//那么这个bind在 count_if中怎么写呢?这里只要知道了vec.begin()的值是会替换placeholders::_1 自然就知道怎么写了
	num = count_if(vec.begin(), vec.end(), bind(greater<int>(), placeholders::_1, 68));
	cout << "dayu 68的个数为:" << num << endl;
}

bind1st的用法 bind2nd的用法

//bind1st(less<int>(), 67)的意思就是,将 less<int>的第1个参数指定为67,第2个参数会由vec1.begin()传入

    //bind2nd(greater<int>(), 68)的意思就是,将 greater<int>的第二个参数指定为68,第一个参数会由vec1.begin()传入
 

class Teacher8 {
public:
	bool operator()(int value1) {
		return value1 > 68;
	}
};
void main() {
	//bind 使用举例,在C++11之前叫做bind1st, bind2nd
	vector<int> vec = { 68,98,23456,68,68,93569,89898 };
	//我们目前是想要统计等于68的个数
	int num = count(vec.begin(), vec.end(), 68);
	cout << "68的个数为:" << num << endl;

	//我们目前是想要统计>68的个数,自己写一个函数对象实现
	num = count_if(vec.begin(), vec.end(), Teacher8());
	cout << "dayu 68的个数为:" << num << endl;

	//我们目前是想要统计>68的个数,想要用C++提供了函数对象实现。
	//查了一下,发现,好像没有一个和具体值比较的。
	//就这个 greater<type>()比较接近,但是传递的是两个参数,一个是vec.begin()的值,一个是vec.end()的值
	//这时候就要用到bind 将 greater<int>的一个参数绑定,那么绑定哪一个呢?
	//这时候就要查看一下 greater<int> 中的operator()方法的实现了,如下:
			//constexpr bool operator()(const _Ty& _Left, const _Ty& _Right) const
			//{	// apply operator> to operands
			//	return (_Left > _Right);
			//}
	//我们发现,返回值是 left> right,也就是如果我们要统计 大于 68的,那么第二个参数就应该是68


	auto aa= bind(greater<int>(),placeholders::_1,68);//就像这样,那么 placeholders::_1怎么理解呢?表示该 适配器调用时 传进去的第一个参数
	bool res = aa(90);//因为90 > 68 的,因此res的值是1
	cout << "res = " << res << endl;
	//那么这个bind在 count_if中怎么写呢?这里只要知道了vec.begin()的值是会替换placeholders::_1 自然就知道怎么写了
	num = count_if(vec.begin(), vec.end(), bind(greater<int>(), placeholders::_1, 68));
	cout << "bind dayu 68的个数为:" << num << endl;

	//使用bind1st
	vector<int> vec1 = { 68,98,23456,68,68,93569,89898 };
	//bind2nd(greater<int>(), 68)的意思就是,将 greater<int>的第二个参数指定为68,第一个参数会由vec1.begin()传入
	num = count_if(vec1.begin(), vec1.end(), bind2nd(greater<int>(),68));
	cout << "bind2nd dayu 68的个数为:" << num << endl;


	//bind1st(less<int>(), 67)的意思就是,将 less<int>的第1个参数指定为67,第2个参数会由vec1.begin()传入
	num = count_if(vec1.begin(), vec1.end(), bind1st(less<int>(), 67));
	cout << "bind1st dayu 67的个数为:" << num << endl;
}

再解释一下:

count_if:是算法

bind:是算法适配器

greater<int>():是系统提供的仿函数

bind();

    num = count_if(vec.begin(), vec.end(), bind(greater<int>(), placeholders::_1, 68 ));

bind(greater<int>(), placeholders::_1, 68 );

如上这一行的意思是:greater有两个参数,第一个我用bind占用了,第二个是固定的68.

bind占用的这个位置,是 vec.begin()传递过来的第一个值,恰好,vec.begin()就只会传递一个值过来。

如果我们这里将 placeholders::_1改成placeholders::_2,跑起来会有run time exception,提示没有第二个参数,这是因为 vec.begin() 只能传递一个参数。

四 迭代器适配器

reverse_iterator 反向迭代器

void main() {
	vector<int> vec = { 100,200,300 };
	for_each(vec.begin(), vec.end(), [](int value) {
		cout << value << endl;
	});

	for_each(vec.rbegin(), vec.rend(), [](int value) {
		cout << value << endl;
	});
}

100
200
300
300
200
100

总结:

  • 9
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值