将复杂函数变量作为参数传递

时间:2012-02-02 13:08:47

标签: c++ templates functor

说我有以下模板功能:

template <class T>
void apply(const vector<complex<T> >& in, vector<T>& out, T (*f)(complex<T>))
{
    out.resize(in.size());
    for(size_t i = 0; i < in.size(); ++i) out[i] = f(in[i]);
}

你可以看到,我只是想将一个函数应用于复杂数据的向量,并将结果存储到实际数据的向量中。我认为这对于整个功能列表应该是好的:abs,norm,real,imag等。

我的问题是,如何传递函数?

我尝试了apply(in, out, abs)的变种,为abs提供了不同的模板而没有运气。我很确定问题源于复杂的所有模板的功能,但我不确定如何正确传递它。谢谢你的帮助。

2 个答案:

答案 0 :(得分:4)

问题是std::abs(来自<complex>)将std::complex<T>参数作为引用到const。您的函数指针仅按值表示,这会导致不匹配。以下代码编译得很好:

#include <vector>
#include <complex>

template <class T>
void apply(const std::vector<std::complex<T> >& in, std::vector<T>& out,
           T (*f)(std::complex<T> const&))
{
    out.resize(in.size());
    for(size_t i = 0; i < in.size(); ++i)
      out[i] = f(in[i]);
}

int main(){
  std::vector<std::complex<float> > vcomp;
  std::vector<float> vf;
  apply(vcomp, vf, &std::abs<float>);
}

Live example on Ideone.

然而,更好的想法是将函数类型作为模板参数:

template <class T, class F>
void apply(const std::vector<std::complex<T> >& in, std::vector<T>& out, F f)
{
    out.resize(in.size());
    for(size_t i = 0; i < in.size(); ++i)
      out[i] = f(in[i]);
}

Live example on Ideone.

在任何情况下,如果某个函数被模板化并且过载,您有时可能需要使用强制转换消除歧义;我不记得{{1函数,但你永远不知道。)

<complex>

答案 1 :(得分:0)

据我所知,您甚至不需要发明apply,因为您可以使用std::transform完成您的工作:

#include <vector>
#include <complex>
#include <algorithm>

int main(){
  std::vector<std::complex<double> > complex_vec(10);
  std::vector<double> double_vec;
  double_vec.resize(complex_vec.size());
  std::transform(complex_vec.begin(), complex_vec.end(),
                 double_vec.begin(), std::abs<double>);
  return 0;
}