2012-05-21 24 views
4

您好,我正在尝试编写一个小程序来模拟GNU科学库中使用微分方程包的动态系统。问题不是特定于GSL,但我只是给你所有的细节GSL中的静态虚拟解决方法

在当前的设计中,我想要一个抽象的Experiment类,其中所有复杂的函数将由gsl库调用。显式系统的动力学将由两个函数定义,即func和jacob,分别定义特定的运动方程和雅可比行列式。因此,我想在Experiment类中执行所有的模拟,并且只覆盖具有将由Experiment继承的特定类的两个虚拟函数。

我的问题是,由于虚拟的这些方法不编译

error: argument of type ‘int (Experiment::)(double, const double*, double*, void*)’ does not match ‘int (*)(double, const double*, double*, void*)’

如果我让这两个功能的静态程序编译,但我失去的是我想达到的具体问题的功能。

显然,它们不能同时是静态的和虚拟的,所以有人知道这个问题的解决方法吗?有没有更好的方法来处理它?

在此先感谢。

编辑:下面编译代码,但他们不是虚拟

class Experiment 
{ 
public: 
    Experiment(); 
    ~Experiment(); 

    void setupExperiment(); 
    static int func(double t, const double y[], double f[], void *params); 
    static int jac (double t, const double y[], double *dfdy, double dfdt[], void *params); 
}; 

void Experiment::setupExperiment(){ 

    double mu = 10; 

    gsl_odeiv2_system sys = {func, jac, 2, &mu}; //Here is the problem with virtual functions 
} 

class aSpecificProblem: public Experiment{ 

    // I want to implement just the func and jac function which should be virtual above 
}; 

回答

6

我相信在你的函数定义的void*是用户指定的回调参数。在这种情况下,使用此参数将指针传递给对象,并使您的回调成为静态函数。在此静态函数内部,将此指针转换回适当的类型(Experiment*)并调用该函数的非静态版本。

class Experiment 
{ 
public: 
    Experiment(); 
    ~Experiment(); 

    void setupExperiment(); 
    static int static_func(double t, const double y[], double f[], void *params); 
    static int static_jac (double t, const double y[], double *dfdy, double dfdt[], void *params); 
    virtual int func(double t, const double y[], double f[]); 
    virtual int jac (double t, const double y[], double *dfdy, double dfdt[]); 
}; 

void Experiment::setupExperiment() 
{ 
    gsl_odeiv2_system sys = {static_func, static_jac, 2, this}; //Here is the problem with virtual functions 
} 

int Experiment::static_func(double t, const double y[], double f[], void *params) 
{ 
    return ((Experiment*)params)->func(t, y, f); 
} 

int Experiment::static_jac (double t, const double y[], double *dfdy, double dfdt[], void *params) 
{ 
    return ((Experiment*)params)->jac(t, y, dfdy, dfdt); 
} 

class aSpecificProblem: public Experiment 
{ 
public: 
    virtual int func(double t, const double y[], double f[]); 
    virtual int jac (double t, const double y[], double *dfdy, double dfdt[]); 
}; 
+0

感谢您付出的努力。它看起来像一个解决方案,我现在要去测试它。再次感谢! – gpierris