ODESystem.h

Go to the documentation of this file.
00001 #ifndef ODESYSTEM_H_
00002 #define ODESYSTEM_H_
00003 
00004 #include <gsl/gsl_errno.h>
00005 #include <gsl/gsl_matrix.h>
00006 #include <gsl/gsl_odeiv.h>
00007 
00008 #include <string>
00009 using std::string;
00010 
00011 #include <iostream>
00012 using std::cerr;
00013 using std::endl;
00014 
00015 namespace odeiv {
00016 
00017     class ODESystem {
00018 
00019         public:
00020             ODESystem( size_t dim ) {
00021                 gsl_sys.function = __int__dydt__;
00022                 gsl_sys.jacobian = NULL;
00023                 gsl_sys.dimension = dim;
00024                 gsl_sys.params = (void *)this;
00025             };
00026 
00027             void setSystem( ODESystem *sys ) {
00028                 gsl_sys.params = (void *)sys;
00029             };
00030 
00031             virtual ~ODESystem() { }
00032             ;
00033 
00034             virtual void derivatives( double t, const double y[], double f[] ) = 0;
00035 
00036             int dimension() const {
00037                 return gsl_sys.dimension;
00038             };
00039 
00040         private:
00041             friend class GslStepper;
00042             friend class AdaptiveStepSolver;
00043             gsl_odeiv_system gsl_sys;
00044             static int __int__dydt__( double t, const double y[], double f[], void *params ) {
00045                 (( ODESystem* )( params ))->derivatives( t, y, f );
00046                 return GSL_SUCCESS;
00047             }
00048     };
00049 
00050 
00051     class Stepper {
00052 
00053         public:
00054 
00055             Stepper( ) {
00056                 /* NOOP */
00057             };
00058 
00059             virtual ~Stepper( ) {
00060                 /* NOOP */
00061             };
00062 
00063             //        virtual const gsl_odeiv_step_type *type()=0;
00064             virtual void reset( ) = 0;
00065             virtual string name() = 0;
00066             virtual int order() = 0;
00067             virtual void apply( double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], ODESystem  & sys ) = 0;
00068 
00069     };
00070 
00071     class GslStepperType {
00072         public:
00073             virtual ~GslStepperType() {}
00074             ;
00075             virtual const gsl_odeiv_step_type *gsl_type() const =0;
00076     };
00077 
00078     class RungeKutta2 : public GslStepperType {
00079         public:
00080             virtual const gsl_odeiv_step_type *gsl_type() const {
00081                 return gsl_odeiv_step_rk2;
00082             };
00083     };
00084 
00085     class RungeKutta4 : public GslStepperType {
00086         public:
00087             virtual const gsl_odeiv_step_type *gsl_type() const  {
00088                 return gsl_odeiv_step_rk4;
00089             };
00090     };
00091 
00092     class GslStepper : public Stepper {
00093 
00094         public:
00095             GslStepper( ODESystem & sys, GslStepperType const& step ) : int_step( NULL ) {
00096                 int_step = gsl_odeiv_step_alloc( step.gsl_type(), sys.dimension() );
00097             };
00098 
00099             virtual ~GslStepper( ) {
00100                 if( int_step )
00101                     gsl_odeiv_step_free( int_step );
00102             };
00103 
00104             virtual void reset( ) {
00105                 gsl_odeiv_step_reset( int_step );
00106             };
00107 
00108             virtual string name() {
00109                 return string( gsl_odeiv_step_name( int_step ) );
00110             };
00111 
00112             virtual int order() {
00113                 return gsl_odeiv_step_order( int_step );
00114             };
00115 
00116             virtual void apply( double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], ODESystem  & sys ) {
00117                 gsl_odeiv_step_apply( int_step, t, h, y, yerr, dydt_in, dydt_out, &sys.gsl_sys );
00118             };
00119 
00120         protected:
00121             friend class AdaptiveStepSolver;
00122             gsl_odeiv_step *int_step;
00123 
00124     };
00125 
00126 
00127     class Solver {
00128 
00129         public:
00130 
00131             Solver( ODESystem & sys, GslStepperType const& step ) : stepper( sys, step ) {
00132                 _y_ = new double[sys.dimension()];
00133             };
00134 
00135             virtual ~Solver() {
00136                 if ( _y_ )
00137                     delete _y_;
00138             };
00139 
00140             virtual void reset( double dt, ODESystem  & sys, const double y0[] ) = 0;
00141 
00142             virtual void advance( double t, double dt, ODESystem  & sys ) = 0;
00143 
00144             double y( size_t i ) {
00145                 return _y_[ i ];
00146             };
00147 
00148         protected:
00149             GslStepper stepper;
00150             double *_y_;
00151     };
00152 
00153     class FixedStepSolver : public Solver {
00154 
00155         public:
00156             FixedStepSolver( ODESystem & sys, GslStepperType const& step );
00157             virtual ~FixedStepSolver();
00158             //virtual void init( ODESystem &sys );
00159             virtual void reset( double dt, ODESystem & sys, const double y0[] );
00160             virtual void advance( double t, double dt, ODESystem  & sys );
00161 
00162         private:
00163             double *dydt_in, *dydt_out, *y_err;
00164     };
00165 
00166 
00167     class AdaptiveStepSolver : public Solver {
00168 
00169         public:
00170             AdaptiveStepSolver( ODESystem & sys, GslStepperType const& step );
00171             virtual ~AdaptiveStepSolver();
00172             // virtual void init( ODESystem & sys );
00173             virtual void reset( double dt, ODESystem & sys, const double y0[] );
00174             virtual void advance( double t, double dt, ODESystem  & sys );
00175 
00176         private:
00177             gsl_odeiv_control *int_control;
00178             gsl_odeiv_evolve *int_evolve;
00179             double h;
00180     };
00181 
00182 
00183 }
00184 #endif /*ODESYSTEM_H_*/

Generated on Wed Jul 9 16:34:39 2008 for PCSIM by  doxygen 1.5.5