要想使用stl配接器算法,unary_function、binary_function的仿函数就必须使用.
先来看STL已经提供的仿函数
—
算法类仿函数
加法: plus<T>
减法:minus<T>
乘法:multiplies<T>
除法:divides<T>
模取:modulus<T>
否定:negate<T>
(一元)
关系仿函数
等于:equal_to<T>
不等于:not_equal_to<T>
大于:greater<T>
大于或等于:greater_equal<T>
小于:less<T>
小于或等于:less_equal<T>
逻辑运算仿函数
and: logical_and<T>
or: logical_or<T>
not: logical_not<T>
选择和投射
select1st<T>
select2nd<T>
对于此类,是针对pair的,传入pair,并返回第一个元素或第二个元素project1st<T>
project2nd<T>
对于此类,是针对多参数的,传入俩个参数,只返回第一个元素或第二个元素
—
再看配接器
函数名 | 实际效果 | 实际对象 |
---|---|---|
bind(_Farg0::* const _Pmd, _Arg0&& _A0) | 11的新特性,auto配合万能绑定,参数能支持到20个参数,对成员函数绑定时第一个参数默认为传入对象 |
|
bind1st(const op& op, const T& x) | op(x, param) | binder1st |
bind2nd(const op& op, const T& x) | op(param, x) | binder2nd |
not1(const Pred& pred) | !pred(param) | unary_negate |
not2(const Pred& pred) | !pred(param1, param2) | binary_negate |
compose1(const Op1& op1, const Op2& op2) | op1(op2(param)) | unary_compose |
compose2( const Op1& op1, const Op2& op2, const Op3& op3) |
op1(op2(param), op3(param)) |
binary_compose (op1, op2, op3) |
ptr_fun(Result(*fp)(Arg)) | fp(param) | pointer_to_unary_function |
ptr_fun(Result(*fp)(Arg1, Arg2)) | fp(param1, param2) | pointer_to_binary_function |
mem_fn() | 11的新特性,auto配合,和bind绑定成员函数块差别不大,第一个参数默认为传入对象 |
|
mem_fun(S (T::*f)()) | (param->*f)() | mem_fun_t |
mem_fun(S (T::*f)() const) | (param->*f)() | const_mem_fun_t |
mem_fun_ref(S (T::*f)()) | (param.*f)() | mem_fun_ref_t |
mem_fun_ref(S (T::*f)() const) | (param.*f)() | const_mem_fun_ref_t |
mem_fun1(S (T::*f)(A)) | (param->*f)(x) | mem_fun1_t |
mem_fun1(S (T::*f)(A) const) | (param->*f)(x) | const_mem_fun1_t |
mem_fun1_ref(S (T::*f)(A)) | (param.*f)(x) | mem_fun1_ref_t |
mem_fun1_ref(S (T::*f)(A) const) | (param.*f)(x) | const_mem_fun1_ref_t |
bind
++ 123456789101112131415161718192021222324252627282930313233343536373839404142434445
double my_divide (double x, double y) {return x/y;}struct MyPair {double a,b;double multiply() {return a*b;}};struct Foo { void print_sum(int n1, int n2) { std::cout << n1+n2 << '\n'; } int data = 10;};int main () {using namespace std::placeholders; //这里注意 adds visibility of _1, _2, _3,...// binding functions:auto fn_five = std::bind (my_divide,10,2); // returns 10/2std::cout << fn_five() << '\n'; // 5auto fn_half = std::bind (my_divide,_1,2); // returns x/2std::cout << fn_half(10) << '\n'; // 5auto fn_invert = std::bind (my_divide,_2,_1); // returns y/xstd::cout << fn_invert(10,2) << '\n'; // 0.2auto fn_rounding = std::bind<int> (my_divide,_1,_2); // returns int(x/y)std::cout << fn_rounding(10,3) << '\n'; // 3MyPair ten_two {10,2};// binding members:auto bound_member_fn = std::bind (&MyPair::multiply,_1); // returns x.multiply()std::cout << bound_member_fn(ten_two) << '\n'; // 20auto bound_member_data = std::bind (&MyPair::a,ten_two); // returns ten_two.astd::cout << bound_member_data() << '\n'; Foo foo;auto f3 = std::bind(&Foo::print_sum, foo, 95, _1);f3(5);
|
|
bind1st
bind2nd
++ 123456789101112131415
int fun(int a, int b){ cout << a - b << endl;; return 0;}int _tmain(int argc, _TCHAR* argv[]){ int a[] = {1, 2, 3, 4}; for_each(a, a+4, bind1st(ptr_fun(fun), 2));//此处由于,bind1st要传入适配器,所以要么fun继承前面的多元函数,要么如此处理 for_each(a, a+4, bind2nd(ptr_fun(fun), 2)); system("pause"); return 0;}
|
|
not1
++ 123
count_if(a, a+5, not1(bind2nd(less<int>(), 4)))//统计大于等于4的个数
|
|
not2
++ 123
int h = accumulate(a, a+5, 4, not2(ptr_fun(fun)));//此中的not2然并卵作用,主要是自己无法想到好的二元算法了
|
|
compose1
compose2
它是GNU的所以vs STL没有,有源码如下++ 123456789101112131415161718192021222324252627282930313233343536373839404142
template<class _Fn1, class _Fn2>class unary_compose : public unary_function<typename _Fn2::argument_type, typename _Fn1::result_type>{ // functor adapter _Func(stored, right)public: typedef unary_function<typename _Fn2::argument_type, typename _Fn1::result_type> _Base; typedef typename _Base::argument_type argument_type; typedef typename _Base::result_type result_type; unary_compose(const _Fn1& _Func1, const _Fn2& _Func2) : op1(_Func1), op2(_Func2) { // construct from functor and left operand } result_type operator()(const argument_type& _Value) const { // apply functor to operands return (op1(op2(_Value))); } result_type operator()(argument_type& _Value) const { // apply functor to operands return (op1(op2(_Value))); }protected: _Fn1 op1; // the functor to apply _Fn2 op2; // the functor to apply}; template<class _Fn1,class _Fn2> inlineunary_compose<_Fn1, _Fn2> compose1(const _Fn1& _Func1, const _Fn2& _Func2){ // return a unary_compose functor adapter return (unary_compose<_Fn1, _Fn2>(_Func1, _Func2));}for_each(a, a+5, compose1(bind2nd(multiplies<int>(), 2), bind2nd(plus<int>(), 2)));
|
|
ptr_fun
上面已经有代码演示,无需
mem_fun
成员对象必须是指针++ 12345678910111213141516171819202122
vector <string*> numbers;// populate vector of pointers:numbers.push_back ( new string ("one") );numbers.push_back ( new string ("two") );numbers.push_back ( new string ("three") );numbers.push_back ( new string ("four") );numbers.push_back ( new string ("five") );vector <int> lengths ( numbers.size() );transform (numbers.begin(), numbers.end(), lengths.begin(), mem_fun(&string::length)); for (int i=0; i<5; i++) { cout << *numbers[i] << " has " << lengths[i] << " letters.\n";}// deallocate strings:for (vector<string*>::iterator it = numbers.begin(); it!=numbers.end(); ++it) delete *it;
|
|
mem_fun1
这个函数并不像
实际效果
那样,它应该是俩个参数,且各个绑定不同。
此函数11之后被淘汰
|
|
mem_fun_ref
mem_fun1_ref
它们和
mem_fun
区别在于,iterator是对象,而不是指针。
mem_fun1_ref此函数11之后被淘汰
mem_fn
++ 12345
dd a;auto triple = std::mem_fn(&dd::aa);cout << triple(a, 2) << endl;//以a为调用对象,传入2
|
|