Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026 #include <ODE/ODESolver.H>
00027
00028
00029
00030 defineTypeNameAndDebug(Foam::ODESolver, 0);
00031 namespace Foam
00032 {
00033 defineRunTimeSelectionTable(ODESolver, ODE);
00034 };
00035
00036
00037
00038
00039 Foam::ODESolver::ODESolver(const ODE& ode)
00040 :
00041 n_(ode.nEqns()),
00042 yScale_(n_),
00043 dydx_(n_)
00044 {}
00045
00046
00047
00048
00049 void Foam::ODESolver::solve
00050 (
00051 const ODE& ode,
00052 const scalar xStart,
00053 const scalar xEnd,
00054 scalarField& y,
00055 const scalar eps,
00056 scalar& hEst
00057 ) const
00058 {
00059 const label MAXSTP = 10000;
00060
00061 scalar x = xStart;
00062 scalar h = hEst;
00063 scalar hNext = 0;
00064 scalar hPrev = 0;
00065
00066 for (label nStep=0; nStep<MAXSTP; nStep++)
00067 {
00068 ode.derivatives(x, y, dydx_);
00069
00070 for (label i=0; i<n_; i++)
00071 {
00072 yScale_[i] = mag(y[i]) + mag(dydx_[i]*h) + SMALL;
00073 }
00074
00075 if ((x + h - xEnd)*(x + h - xStart) > 0.0)
00076 {
00077 h = xEnd - x;
00078 hPrev = hNext;
00079 }
00080
00081 hNext = 0;
00082 scalar hDid;
00083 solve(ode, x, y, dydx_, eps, yScale_, h, hDid, hNext);
00084
00085 if ((x - xEnd)*(xEnd - xStart) >= 0.0)
00086 {
00087 if (hPrev != 0)
00088 {
00089 hEst = hPrev;
00090 }
00091 else
00092 {
00093 hEst = hNext;
00094 }
00095
00096 return;
00097 }
00098
00099 h = hNext;
00100 }
00101
00102 FatalErrorIn
00103 (
00104 "ODESolver::solve"
00105 "(const ODE& ode, const scalar xStart, const scalar xEnd,"
00106 "scalarField& yStart, const scalar eps, scalar& hEst) const"
00107 ) << "Too many integration steps"
00108 << exit(FatalError);
00109 }
00110
00111