# NDSolve with Piecewise function

I have the following code on Mathematica

paramFinal = {\[Rho] -> 0.05, price -> 0.05, \[Gamma] -> 0.5, \[Omega] -> 0.8, d -> 1, a -> 0.3, b -> 0.1, r -> 0.7, \[Gamma] -> 0.6, Subscript[g, y] -> 0.9, \[Delta] -> 0.1, \[Eta] -> 2.65, \[Psi] -> 1, pbar -> 0.5, hbar -> 0.25, Subscript[\[CapitalOmega], 1] -> 0.5, Subscript[\[CapitalOmega], 2] -> 0.6};


I have a function

z[x_] := x^2


NDsolve command with Piecewise command :

NDSolve[ v'[t] == (r v[t] - (price b  v[t])/Piecewise[{{z'[p[t]], pbar >
p[t]}, {pbar, pbar < p[t]}}]) /. paramFinal, p'[t] == Piecewise[{{-((p[t]
z'[p[t]])/z''[p[t]]) /. paramFinal, pbar > p[t]}, {0, pbar < p[t]}}], v[0]
== 0.024752227722772267, p[0] == 0.025, {v[t], p[t]}, {t, 0, 100}]


I have the following error code :

NDSolve::dsvar: v[0]==0.0247522 cannot be used as a variable. >>

I don't see why it says that Piecewise is not list of pairs. How can I fix this error and turn the code without error ?

• Piecewise[{{z'[p[t]], pbar > p[t]}, {pbar, pbar < p[t]}}] be careful !! Nov 6, 2017 at 18:56
• $a$ is assigned as 0, so there is no $a(t)$ nor $a'(t)$. Please revise your equations and parameters Nov 6, 2017 at 19:01
• Thanks, I see the error, I am trying to revise it Nov 6, 2017 at 19:03
• @JoséAntonioDíazNavas I have always the same error altough I have changed the variable $a$ by $v$ in order to avoid the conflict between parameters. Nov 6, 2017 at 19:08
• equations and initial condition must be also within {} inside NDSolve Nov 6, 2017 at 19:10

It looks like this problem can be solved analytically without the extra condition on the p derivative, with a change in the piecewise function to an equivalent UnitStep fn.

dep = p'[t] == -p[t]^2 UnitStep[t - pbar]

DSolve[{dep, p[0] == .25}, p[t], t] // Flatten
{p[t] -> 1./(-1. pbar UnitStep[t - pbar] + 1. t UnitStep[t - pbar] +
1. pbar UnitStep[-1. pbar] + 4.)}

p[t_] = p[t] /. %;

Plot[Evaluate[p[t] /. paramFinal], {t, -5, 30}]


Use that in the v equation

veq = v'[t] == (r v[t] - (price b v[t])/
Piecewise[{{z'[p[t]], pbar > p[t]}, {pbar, pbar < p[t]}}]) /.
paramFinal

DSolve[{veq, v[0] == 0.024752227722772267}, v[t], t] // Flatten

{v[t] -> (0.0247522 E^(0.69 t) -
0.0247445 E^(0.69125 t - 0.00125 t^2)) UnitStep[1/2 - t] +
0.0247445 E^(0.69125 t - 0.00125 t^2)}

v[t_] = v[t] /. %

Plot[v[t], {t, -5, 5}]


There are a couple of issues here, including some related to input syntax. Something that you might want to consider is that one of the equations in your system can be solved independently. In particular, the second equation is purely a function of p[t]. Therefore, it probably makes more sense to solve that problem first (notwithstanding that you will need another initial condition), then use that solution to solve the first differential equation. A possible solution strategy might look something like this:

sol = NDSolve[{p'[t] ==
Piecewise[{{-((p[t] D[z[p[t]], t])/D[z[p[t]], {t, 2}]) /.
paramFinal, pbar > p[t]}, {0, pbar < p[t]}} /. paramFinal],
p[0] == 0.0249998, p'[0] == 4}, p[t], {t, 0, 2}]


Note: I have assumed some initial condition value for the first derivative of p[t].

Now with a numeric representation of p[t] we can solve the first problem in the original system.

sol2 = NDSolve[{afun'[
t] == -(r afun[t] - (price b afun[t])/
Piecewise[{{z'[p[t]], pbar > p[t]}, {pbar, pbar < p[t]}} /.
paramFinal /. sol[[1]]]) /. paramFinal,
afun[0] == 0.0247522}, afun[t], {t, 0, 2}]