int i; mutable int j;
public:
A(int ii, int jj) : i(ii), j(jj) {};
void set_i(int x) { i = x; };
void set_j(int x) const { j = x; };
};
A a(0,0); int k = 1;
bind(&A::set_i, &a, _1)(k); // a.i == 1
bind(&A::set_j, &a, _1)(k); // a.j == 1
&a为指针,所以const的是a的指针,不是a本身,所以可以调用set_i
bind(&A::set_i, a, _1)(k); // error; a const copy of a is stored.
// Cannot call a non-const function set_i
bind(&A::set_j, a, _1)(k); // a.j == 0, as a copy of a is modified
如果形如:
A a(0,0);
bind(&A::set_i, _1, 1)(a); // a.i == 1
bind(&A::set_j, _1, 1)(a); // a.j == 1
因为a是参数,参数永远都是引用,所以可以调用
F f;
...
bind(f, _1); // fails, cannot deduce the return type
ret<int>(bind(f, _1)); // ok
...
bind(f, 1); // fails, cannot deduce the return type
ret<int>(bind(f, 1)); // fails as well!
结构体F没有定义result_type
对于一个零元的lambda表达式无法推导出返回类型
bind<int>(f, 1); // ok
var(x) creates a nullary lambda functor
lambda的左侧必须是luamb表达式
:: /
./
.*这3种运算符不能重载
成员指针操作符:
struct A { int d; };
A* a = new A();
...
(a ->* &A::d); // returns a reference to a->d
(_1 ->* &A::d)(a); // likewise
bind,2种方式:
bind(target-function, bind-argument-list)
bind(target-member-function, object-argument, bind-argument-list)
函数指针或引用作为目标参数,可以是bound/unbound
X foo(A, B, C); A a; B b; C c;
bind(foo, _1, _2, c)(a, b);
bind(&foo, _1, _2, c)(a, b);
bind(_1, a, b, c)(foo);
//"_1"是右边括号中的"_1 - _2"(几天不看有点忘了)
bind(_1, _2, _3)(_1 - _2, a, b)
//"1.0"参数实例化
bind(_1, 1.0)(_1 + _1)
"var"将参数lambda化,此处var(b)可以是被解释为指针或引用,否则bind(&base::foo, b); foo为b的纯虚函数->编译报错
bind(&base::foo, var(b))()
*************************注意的地方*************************
①左边的操作符必须是一个lambda表达式
int i;
i = _1;
改正方法:
var(i) = _1; ---> var可以表达式转为一个lambda
②
struct A {...};
A *a = new A();
(a->* &A::foo)(1);
(a->*&A::mem_val);
"&"不可以省略
③
struct which_one {
typedef pftr_type (*result_type)(bool x);
template<class T>
struct sig {
typedef result_type type;
};
result_type operator()()const { return sum_or_product; }
};
which_one wo;
std::cout << bind(bind(bind(wo), _1), _2, _3)(true, 2, 4) << std::endl;
需说明的几个地方:(sig还是不是很清楚%>_<%)
1.bind(wo);由于这个函数对象不要参数,因此bind(wo)()等于wo(), bind(wo)只是返回一个函数对象//bind都是返回函数对象
为什么bind(two)不能直接改成two,因为bind(bind(two), _1),若改成two,bind(two, _1),显然"two"是不需要参数的。而原先的是返回"sum_or_product"
2. 将sig struct注释掉,保留result_type,编译运行正常,把所有的result_type改成result_type2或者其他什么名字,编译正常。
struct with_result_type {
typedef int result_type;
int operator()() const { return 123; }
}; 这个地方去掉typedef int result_type;也出错,说明使用函数对象时,result_type的定义是必须的
3.unlambda:一个包装在 unlambda
中的 lambda 仿函数不再是一个 lambda 仿函数,也不再参与参数替换过程
自己尝试的struct sig小例子:
int sum_1(int a) { return a; }
struct with_result_type {
//typedef int result_type;
template< class Args >
struct sig {
typedef int type;
};
typedef int (*pfn)(int);
template< class Args, class A1 >
struct sig<Args(A1)>{
typedef pfn type;
};
int operator()() const { return 123; }
pfn operator()(int) const { return sum_1; }
};
with_result_type test;
std::cout << bind(test)() << std::endl;
std::cout << test(3)(456) << std::endl;