0
#include <iostream> 
#include <boost/bind.hpp>

struct FCall3Templ {

  template<typename ARG1, typename ARG2>
  ARG1 operator()(ARG1 arg1, ARG2 arg2) {
    return arg1+arg2;
  }
};
int main() {
  boost::bind<int>(FCall3Templ(), 45, 56)(); // call 1
  boost::bind<double>(FCall3Templ(), 45.0, 56.0)(); // call 2
  return 0;
}

我发布的代码与您可以在此处找到的代码相同。

我对元编程、boost::bind 和运算符重载相对较新,但我不明白这段代码在代码的某些部分中做了什么,我有这个问题:

  • 为什么operator()在不指定该运算符的标签的情况下使用?什么是重载/定义?
  • 我应该如何使用赋值来捕获和存储 2 个调用返回的值T var = ?
  • ()两个调用中最后一个都是空的事实是什么意思?是接线员的电话吗?那么这种技术/操作符的名称是什么?
  • 为什么以这种方式使用运算符重载而不是仅使用方法?

谢谢。

4

2 回答 2

3

好的,首先,类型FCall3Templ是函子,两个参数operator()意味着您可以创建一个实例并像这样“调用”它:

FCall3Templ f; // instantiate it
int i = f(45, 56); // call it, sums the numbers and returns the result

接下来,boost::bind可用于制作另一个具有较少参数的可调用对象。在这种情况下:

boost::bind<int>(FCall3Templ(), 45, 56);

它接受一个FCall3Templ实例,并创建一个可以在没有参数的情况下调用的仿函数,它的作用与调用相同f(45, 56)。换句话说,它将函子“绑定”到两个参数值。最后一行等价于但不完全相同

boost::bind<int>(f, 45, 56);

您可以通过将返回值分配给变量来捕获该值,就像您对任何函数所做的那样:

int n = boost::bind<int>(FCall3Templ(), 45, 56);

最后,我们在这里调用这样一个仿函数的临时实例:

boost::bind<int>(FCall3Templ(), 45, 56)();

其中最终的()意思是我们称为无参数仿函数,如果像这样表示(未经测试)会更清楚:

boost::function<int()> f2 = boost::bind<int>(FCall3Templ(), 45, 56);
int n = f2();
于 2012-08-15T21:13:49.250 回答
3

依次回答您的问题:

1)operator()()对象的运算符。例如,如果您查看std::less的定义,它定义operator()了接受两个参数并进行比较,然后返回结果。这允许你写

  bool foo(int a, int b)
    {
       std::less<int> compare;
       return compare(int a, int b);
    }

2)在这种情况下,您可以像往常一样抓住它们。

int i = boost::bind<int>(FCall3Templ(), 45, 56)(); // call 1     
double d = boost::bind<double>(FCall3Templ(), 45.0, 56.0)(); // call 2    

3)boost::bind用于获取函数对象(已operator()定义的对象)、函数指针或成员函数指针可选地连同参数,并返回一个新的函数对象(其类型难以描述),该对象在调用时使用绑定的参数(以及调用期间可能的参数)。请参阅boost::bind的文档

在这种情况下,答案只是调用boost::bind然后立即调用结果。第二组()正在调用结果。由于所有参数在调用时都已绑定,因此boost::bind不需要额外的参数。

4)原因是最初的问题是询问如何boost::bind自动选择正确的函数模板实例化。不幸的是,当使用函数指针(包括模板函数)时,boost::bind不能自动执行重载解析,因为它必须传递一个函数指针作为它的第一个参数,并且它不知道如何执行重载解析。

但是,如果给定一个函子,并且该函数定义了模板化成员函数operator()甚至重载operator (),则它可以在调用时执行重载决议。

于 2012-08-15T21:21:28.620 回答