8

func()我最近在这段代码中调用时花了一些时间来理解错误消息:

int main()
{
    vector< vector<double> > v;

    double sum = 0;
    for_each( v.begin(), v.end(), 
        bind2nd( ptr_fun(func), &sum ) );

    return 0;
}

func()像这样声明时,代码编译得很好:

void func( vector<double> v, double *sum )
{
}

当我使用这个声明(为了提高效率)时,我得到了一个编译器错误:

void func( const vector<double> &v, double *sum )
{
}

由于 binder2nd 的 operator() 的定义,我希望看到的错误类似于引用到引用的错误,

result_type operator()(const argument_type& _Left) const

相反,令我惊讶的是,Visual C++ (VS2012) 编译器给我的错误是:

错误 C2535:'void std::binder2nd<_Fn2>::operator ()(const std::vector<_Ty> &) const':成员函数已定义或声明

我无法破译。

  • 你能解释一下已经定义的operator()机制

我得到的完整错误是:

error C2535: 'void std::binder2nd<_Fn2>::operator ()(const std::vector<_Ty> &) const' : member function already defined or declared
with
[
     _Fn2=std::pointer_to_binary_function<const std::vector<double> &,double *,void,void (__cdecl *)(const std::vector<double> &,double *)>,
      _Ty=double
]
c:\vc\include\xfunctional(319) : see declaration of 'std::binder2nd<_Fn2>::operator ()' 
with
[
      _Fn2=std::pointer_to_binary_function<const std::vector<double> &,double *,void,void (__cdecl *)(const std::vector<double> &,double *)>
] 
c:\consoleapplication1.cpp(31) : see reference to class template instantiation 'std::binder2nd<_Fn2>' being compiled 
with 
[
       _Fn2=std::pointer_to_binary_function<const std::vector<double> &,double *,void,void (__cdecl *)(const std::vector<double> &,double *)>
]

Build FAILED.
4

2 回答 2

6

这种行为是明确定义的(每个正确的 C++ 编译器都无法编译您的代码)。

D.9.3从类模板的标准(N3376)部分binder2nd,存在这两个定义operator()

typename Fn::result_type
operator()(const typename Fn::first_argument_type& x) const;

typename Fn::result_type
operator()(typename Fn::first_argument_type& x) const;

如果first_argument_type已经是 a const T&,那么它们将是冲突的。

于 2012-09-10T11:18:36.787 回答
0

这不是一个答案,但我只想记录现代 C++11 解决方案,其中所有小型绑定助手都被弃用,取而代之的是通用std::bind

#include <functional>
#include <vector>
#include <algorithm>

void func(std::vector<double> const & v, double * sum) { /* ... */ }

int main()
{
    std::vector<std::vector<double>> v;
    double sum = 0;
    std::for_each(v.begin(), v.end(), std::bind(func, std::placeholders::_1, &sum));
}

C++11 的可变参数模板,以及更全面的类型修改特征集合,提供std::bind了比<functional>.

于 2012-09-10T11:02:12.477 回答