2009年4月4日星期六

【原】Boost库之function的使用

Boost库的function是一组函数对象包装类的模板,实现了一个泛型的回调机制。Boost库的function与函数指针相比,优点在于它允许用户在目标的实现上拥有更大的弹性,即目标既可以是普通函数(自由函数),也可以是函数对象和类成员函数,而且可以给函数添加状态。

使用Boost库的function,可以很好地与现有的代码融合在一起。另外,function还可以与Boost库的bind和lambda配合使用,从而极大地扩展了function的适用范围。function库支持的函数参数个数最多为10个,其头文件为function.hpp或functionX.hpp(其中,X为0到10之间的整数)。如果你的程序中只使用了X个参数的function,那么你可以只包含对应的functionX.hpp,当然,你也可以只包含function.hpp(它包含了所有的functionX.hpp)。
下面介绍function库的具体用法。

◆ 普通函数(自由函数)用法
int Add(int x, int y)
{
return x+y;
}
function<int (int,int)> f; // 或者 function2<int, int, int> f;
f = Add;
cout << "f(2, 3)=" << f(2, 3) << endl;
其中,模板参数的第1个int为返回值类型,后两个int为参数类型。

◆ 函数对象用法
class CStudent
{
public:
void operator() (string strName, int nAge)
{
cout << strName << " : " << nAge << endl;
}
};
function<void (string, int)> f; // 或者 function2<void, string, int> f;
CStudent stu;
f = stu;
cout << "f(\"hello\", 25)=" << f("hujian", 25) << endl;

◆ 成员函数用法
struct TAdd
{
int Add(int x,int y)
{
return x+y;
}
};
TAdd tAdd;
function<int (tAdd *,int,int)> f; // 或者 function<int (tAdd &,int,int)> f;
f = & TAdd::Add;
cout << f(&tAdd, 2, 3); // 如果前面的模板参数为值或引用,直接传入tAdd即可
其中,模板参数的tAdd *为类的实例的指针,当然也可以传入类的实例或其引用,只不过调用时需要做相应的修改。

使用function时,可以通过empty函数或与0比较来判断其是否指向一个有效的函数。如果function没有指向一个有效的函数,调用时会抛出bad_function_call的异常。function的clear函数可以使其不再关联到一个函数或函数对象,如果该function本身就是空的,调用该函数也不会带来任何问题。
以上介绍了function库的最基本的一些用法,关于function库的其他应用,大家可以参考《Beyond the C++ STL》。

3 条评论:

  1. 我觉得我们在介绍一个新东西时最好能讲讲它的优势在哪里,它给我们的应用带来哪些实惠,这个新事物为什么会出现,它解决了我们平时遇到的哪些问题,最好还能够做一些横向与纵向的对比,而不是简简单单做一个介绍,跟百科全书一样。
    就比如这个function,我们为什么要使用它?在什么场合下值得使用?

    回复删除
  2. 主要是全部都讲的话,篇幅太多了。而且介绍这种库,你抽象地去讲好像不太好懂,可能要给出实例并加以分析,但一堆代码贴在帖子里也不太好,我们这个博客显示代码时也没有格式,贴一堆代码的话显得很乱。其实,《Beyond the C++ STL》里面都有这方面的介绍的,帖子末尾也有提到。光靠一个帖子就想把一个库的方方面面都介绍到,好像也不太现实。

    回复删除
  3. 我觉得要解答我提出的这些个问题,似乎不需要贴代码哎,呵呵~
    你讲的这本书,我们有时间会看看。

    回复删除