Re: checking accuracy with stepwise ode.
- To: mathgroup at smc.vnet.net
- Subject: [mg48503] Re: checking accuracy with stepwise ode.
- From: rknapp at wolfram.com (Rob Knapp)
- Date: Wed, 2 Jun 2004 04:22:22 -0400 (EDT)
- References: <c99dsj$k77$1@smc.vnet.net>
- Sender: owner-wri-mathgroup at wolfram.com
sean_incali at yahoo.com (sean kim) wrote in message news:<c99dsj$k77$1 at smc.vnet.net>...
> actually I figured it out, I hate it when I answer my own question
> after posting it. I didn't define the functions with [t_]. that's why
> the NDSOlve complained.
>
> If i use the code below, it works fine, but How do I know the results
> are accurate? Does NDSolve do soemthing different with the stepwise
> functions that it doesn;t do with the normal functions? how do I
> check my results? how do I know the answer that i got is correct? I
> ask because the plot looks kinda funky.
>
>
> Thanks all in advance for any and all comments.
>
> sean
>
> k1 = 1/10; k2 = 1/20;
> a0[t_] := 0 /; t < 0 ;
> a0[t_] := 1/10 /; 0 <= t <= 200 ;
> a0[t_] := 0 /; 200 <= t <= 600 ;
> a0[t_] := 1/10 /; 600 <= t<= 2000;
>
> ndsolution = NDSolve[{b'[t] == -k2 b[t] y[t], x'[t] == -k1 a0[t] x[t]
> + k2 b[t] y[t], y'[t] == k1 a0[t] x[t] - k2 b[t] y[t], b[0] == 1,
> x[0] == 1, y[0] == 0}, {b, x, y}, {t, 0, 2000}][[1]] ;
>
> Plot[Evaluate[{a0[t], b[t], x[t], y[t]} /. ndsolution], {t, 0, 2000},
> PlotStyle -> {
> {AbsoluteThickness[2], RGBColor[0, 0, 0]},
> {AbsoluteThickness[2], RGBColor[.7, 0, 0]},
> {AbsoluteThickness[2],RGBColor[0, .7, 0]},
> {AbsoluteThickness[2], RGBColor[0, 0, .7]}},
> PlotRange -> All, Axes -> False, Frame -> True,
> PlotLabel -> StyleForm[A StyleForm[" B", FontColor -> RGBColor[.7, 0,
> 0]] StyleForm[" X", FontColor -> RGBColor[0, .7, 0]]StyleForm["Y",
> FontColor -> RGBColor[0, 0, .7]],
> FontFamily -> "Helvetica", FontSize -> 12, FontWeight -> "Bold"]];
The methods that are used in NDSolve will not give you full accuracy
except for smooth functions. To get full accuracy from a solution to
the problem above, you need to tell NDSolve where the discontinuities
are. When you do this, NDSolve makes sure to start a new step at the
point of discontinuity. Further recommended when discontinuities are
present is to use "one-step" methods, such as Runge-Kutta methods,
since there is no cost to starting up again after a discontinuity.
For you example:
Find the discontinuiity points once you have defined a0 (you could
type them in, but I was too lazy for this)
In[6]:=
discontinuitypoints =
Union[Cases[
Flatten[Cases[
DownValues[a0],(Less | LessEqual)[x__]\[RuleDelayed]{x}, {0,
Infinity}]], _?NumberQ]]
Out[6]=
{0,200,600,2000}
The discontinuity points are included in the argument to NDSolve which
gives the range for the independent variable, in this case with
Join[{t,0},discontinuitypoints, {2000}]
In[7]:=
sol = NDSolve[{b'[t] == -k2 b[t] y[t],
x'[t] == -k1 a0[t] x[t]+k2 b[t] y[t],
y'[t] == k1 a0[t] x[t]-k2 b[t] y[t],b[0] == 1,x[0] == 1,
y[0] == 0},{b,x,y},Join[{t,0},discontinuitypoints, {2000}],
Method->ExplicitRungeKutta]
Out[7]=
{{b->InterpolatingFunction[{{0.,2000.}},<>],
x->InterpolatingFunction[{{0.,2000.}},<>],
y->InterpolatingFunction[{{0.,2000.}},<>]}}
Rob Knapp
Wolfram Research