bind1st和bind2d使用
大约 3 分钟
bind1st和bind2d使用
- bind1st和bind2d是STL中的;
- bind1st和bind2d作用: 将二元函数对象的一个参数绑定,使其变为一元函数对象;
- 缺点: 只能用于二元函数对象。
- 函数对象: 对象拥有小括号重载函数的对象。
#include <functional> --包含c++库中的所有的函数对象 bind1st
#include <algorithm> --包含了c++库中的所有的泛型算法

例1—改变排序顺序
#include <iostream>
#include <vector>
#include <functional>
#include <algorithm>
#include <ctime>
using namespace std;
template<typename Container>
void showContainer(Container& con)
{
typename Container::iterator it = con.begin();
//编译器是从上到下编译的,这个还没有实例化,它不知道这个名字作用域后面的iterator是类型还是变量
//typename告知编译器后面类型的作用域后面是类型
for (; it != con.end(); ++it)
{
cout << *it << " ";
}
cout << endl;
}
int main()
{
vector<int> vec;
srand(time(nullptr));
for (int i = 0; i < 20; ++i)
{
vec.push_back(rand() % 100 + 1);//随机出来的数字,并不是有序的
}
showContainer(vec);
sort(vec.begin(), vec.end());//默认小到大排序,传入的是起始和末尾的后继的迭代器
showContainer(vec);
//greater 二元函数对象
sort(vec.begin(), vec.end(), greater<int>());//大到小排序
showContainer(vec);
return 0;
}
greater是一个二元函数对象:(因为一次需要从容器中拿2个函数对象出来)


例2—将70按顺序插入到vec容器中
问题:将70按顺序插入到vec容器中
使用find_if函数需要传入一个**一元函数对象(**一次从容器中拿出一个元素和70进行比较 )
注意:库里面提供的函数对象,没有办法直接使用;怎么办?
使用绑定器,将二元函数对象转换为一元函数对象;

#include <iostream>
#include <vector>
#include <functional>
#include <algorithm>
#include <ctime>
using namespace std;
template<typename Container>
void showContainer(Container& con)
{
typename Container::iterator it = con.begin();
for (; it != con.end(); ++it)
{
cout << *it << " ";
}
cout << endl;
}
template<typename Iterator, typename Compare>
Iterator my_find_if(Iterator first, Iterator last, Compare comp)
//遍历这2个迭代器之间的元素,如果满足函数对象的运算,就返回当前迭代器,如果都不满足,返回end()
{
for (; first != last; ++first)
{
if (comp(*first))//comp.operator()(*first)一元函数对象,因为要从容器拿1个元素和它指定的元素比较
//my_find_if需要1元函数对象,而在库里面都是二元的
{
return first;
}
}
return last;
}
template<typename Compare, typename T>
class _mybind1st//绑定器是函数对象的一个应用
{
public:
_mybind1st(Compare comp, T val)
:_comp(comp), _val(val)
{}
bool operator()(const T& second)
{
return _comp(_val, second);//greater
}
private:
Compare _comp;
T _val;
};
//mybind1st(greater<int>(), 70)
//mybind1st就是将函数对象封装了一下。
template<typename Compare, typename T>
_mybind1st<Compare, T> mybind1st(Compare comp, const T& val)
{
//直接使用函数模板,好处是,可以进行类型的推演
return _mybind1st<Compare, T>(comp, val);
}
int main()
{
vector<int> vec;
srand(time(nullptr));
for (int i = 0; i < 20; ++i)
{
vec.push_back(rand() % 100 + 1);
}
showContainer(vec);
sort(vec.begin(), vec.end());//默认小到大排序
showContainer(vec);
//greater 二元函数对象
sort(vec.begin(), vec.end(), greater<int>());//大到小排序
showContainer(vec);
/*
把70按顺序插入到vec容器当中 找第一个小于70的数字
operator()(const T &val)
greater a > b
less a < b
绑定器 + 二元函数对象 =》 一元函数对象
bind1st: + greater bool operator()(70, const _Ty& _Right)
bind2nd: + less bool operator()(const _Ty& _Left, 70)
*/
auto it1 = my_find_if(vec.begin(), vec.end(),
mybind1st(greater<int>(), 70));
//auto it1 = my_find_if(vec.begin(), vec.end(),bind2nd(less<int>(), 70));
if (it1 != vec.end())
{
vec.insert(it1, 70);
}
showContainer(vec);
return 0;
}