Проблема в том, что std::abs
(из <complex>
) принимает параметр std::complex<T>
в качестве ссылки на постоянное значение. Указатель вашей функции говорит только по значению, что вызывает несоответствие. Следующий код компилируется просто отлично:
#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>);
}
Живой пример на 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]);
}
Живой пример на Ideone.
В любом случае вам иногда может понадобиться устранение неоднозначности на сайте вызовов с использованием приведения, если функция шаблонизирована и перегружены (я не помню ни одной лишней из функций <complex>
, но вы никогда не знаете).
// taking std::abs as an example. It's not actually templated *and* overloaded
typedef float (*func_ptr)(std::complex<float> const&);
apply(vcomp, vf, (func_ptr)&std::abs<float>);