MATLAB: How to solve differential equations of motion of second order, which are changing depending on if/else conditions

differential equationsfunctionif statementMATLABode45time

I'm an absolute Matlab beginner and need your help. My problem is a little bit more complex than the question above. Basicaly I have a system of two differential equtions of motion of second order vdoubledot and wdoubledot, here called dv and dw which I want to solve with the help of ode45. The tricky part is, dv and dw will change depending on the if/else conditions shown below and I want a continous plot of the displacements v and w in the end and I also need to pass the parameters v and w to the next function depending on the if/else condition.
I have a few questions and I hope someone can help me there:
1) I gave all functions dv/dw different names depending on the elseif condition. Should I give them the same name? Eg. all named dv = eqm2a(t,v)?
2) How do I pass the displacements v and w from one function to the next (hence the term k2*(v2-v3+-s) in the latter eqm)?
3) I only want to use v0 and w0 for the very first timestep at t=0 and the very first if condition and after that it should autimatically use the current v(ti) and w(ti) when switching to the next if/else statement. How do I do that?
4) And last (for now) but not least: Should I use the if conditions like v(1)-w(1)<=-s like I did below or is v-w<=-s sufficient?
Infos: m1, m2, k2, om, etc. are scalars which are predefined. FW is a time-dependend parameter. The plot(t,v)-command is missing, I'll add that if everything else works as intended. Everything is written as a script.
tspan = [0 100];
v0 = [0 5];
w0 = [0 0];
[t,v] = ode45(@(t,v) eqm2ai(t,v), tspan, v0);
[t,w] = ode45(@(t,w) eqm3ai(t,w), tspan, w0);
[t,v] = ode45(@(t,v) eqm2bii(t,v), tspan, v0);
[t,w] = ode45(@(t,w) eqm3bii(t,w), tspan, w0);
[t,v] = ode45(@(t,v) eqm2biii(t,v), tspan, v0);
[t,w] = ode45(@(t,w) eqm3biii(t,w), tspan, w0);
if -s<v(1)-w(1)<s
function dv = eqm2ai(t,v)
dv = zeros(2,1);
dv(1) = v(2);
dv(2) = my*r*om^2*sin(om*t);
end
function dw = eqm3ai(t,w)
dw = zeros(2,1);
dw(1) = w(2);
dw(2) = (FW-k3*w(1))/m3;
end
elseif v(1)-w(1)<=-s
function dv = eqm2bii(t,v)
dv = zeros(2,1);
dv(1) = v(2);
dv(2) = my*r*om^2*sin(om*t)-(k2*(v(1)-w(1)-s))/(m1+m2);
end
function dw = eqm3bii(t,v)
dw = zeros(2,1);
dw(1) = w(2);
dw(2) = (FW-k3*w(1)+k2*(v(1)-w(1)-s))/m3;
end
elseif v(1)-w(1)>=s
function dv = eqm2biii(t,v)
dv = zeros(2,1);
dv(1) = v(2);
dv(2) = my*r*om^2*sin(om*t)-(k2*(v(1)-w(1)+s))/(m1+m2);
end
function dw = eqm3biii(t,v)
dw = zeros(2,1);
dw(1) = w(2);
dw(2) = (FW-k3*w(1)+k2*(v(1)-w(1)+s))/m3;
end
end

Best Answer

Do you know (before calling the ODE solver the first time) when the ODE function that you're trying to solve changes based on the condition? If so call ode45 to solve the first ODE function up until that point then use the final result from solving that first ODE function as the initial condition for a second ode45 call using the second ODE function.
As a slightly more concrete explanation, let's say you know that the ODE you need to solve changes every 2 seconds. Solve the first ODE with a time span of [0 2]. Use the solution of that first ODE to define the initial condition for the second ODE and solve that second ODE with a time span of [2 4]. Repeat that process, using the solution of the second ODE to generate the initial condition for the third ODE and so on.
If you don't know exactly when the ODE you're trying to solve will change based on the condition, use an Events function. There's an example that uses Events in MATLAB called ballode. It's not exactly the same as the situation you described, since the ODE doesn't change, but if you imagine passing different function handles into the ODE solver based on which condition/event is "active" you should be able to adapt it to suit your purposes.