我希望编写一个函数,该函数使用double函数的返回值,但是/并且我想在函数调用期间选择这个双精度函数。我的想法是:
#include <iostream>
double linea(double a, double b, double x);
double parabola(double a, double b, double c, double x);
void konjgrad(double (*function)(void** params), void** params);
double linea(double a, double b, double x){
return a*x+b;
}
double parabola(double a, double b, double c, double x){
return a*x*x+b*x+c;
}
void konjgrad(double (*function)(void** params), void** params){
double d;
d=function(params);
std::cout<<d<<std::endl;
}
int main(){
konjgrad(linea(1.6,5.1,2.6));
konjgrad(parabola(2.4,3.1,4,2.6));
return 0;
}但我陷入了指针的迷宫中。有没有人知道如何解决这个问题?
发布于 2017-01-24 19:33:28
您可以使用和引入所需的灵活性,而无需任何额外的运行时开销:
template <typename TF, typename... TArgs>
void konjgrad(TF&& f, TArgs&&... args)
{
double d;
d = std::forward<TF>(f)(std::forward<TArgs>(args)...);
std::cout<<d<<std::endl;
}然后,可以按如下方式调用konjgrad:
konjgrad(linea, 1.6, 5.1, 2.6);
konjgrad(parabola, 2.4, 3.1, 4, 2.6);或者,您可以使用,并将绑定参数的负担放在调用者身上:
template <typename TF>
void konjgrad(TF&& f)
{
double d;
d = std::forward<TF>(f)();
std::cout<<d<<std::endl;
}然后,可以按如下方式调用konjgrad:
konjgrad([]{ return linea(1.6, 5.1, 2.6); });
konjgrad([]{ return parabola(2.4, 3.1, 4, 2.6); });发布于 2017-01-24 21:17:23
基于维托里奥·罗密欧的评论编辑了,更新以传递向量作为常量引用,并在直线和抛物线API中添加了必要的断言。
如果你想避免不同的函数,这里有一个很简单的方法。由于你的函数接口定义得很清楚,你可以在你的linea和parabola函数中传入双精度类型参数的向量或数组。
#include <vector>
using namespace std;
double linea(const std::vector<double>& params)
{
assert(params.size() == 3 /*Linear 3 parameters required*/);
return params[0] * params[1] + params[2];
}
double parabola(const std::vector<double>& params)
{
assert(params.size() == 4 /*Parabola 4 parameters required*/);
return params[0] * params[3] * params[3] +
params[1] * params[3] +
params[2];
}稍微修改一下你的konjgrad函数,它现在通过函数指针从底层调用返回双精度值。请注意,第一个参数明确定义了函数接口。第二个参数是双精度向量。
double konjgrad(double(*function)(const std::vector<double>&), const std::vector<double>& params)
{
return function(params);//returning value from here
}最后,这里是您应该如何调用上面定义的API。
int main(int argc, wchar_t* argv[])
{
std::vector<double> vals;
vals.push_back(1.6);
vals.push_back(5.1);
vals.push_back(2.6);
double v1 = konjgrad(linea, vals);
std::vector<double> parab;
parab.push_back(2.4);
parab.push_back(3.1);
parab.push_back(4.0);
parab.push_back(2.6);
double v2 = konjgrad(parabola, parab);
return 0;}
希望这能有所帮助。
https://stackoverflow.com/questions/41827038
复制相似问题