Hello!
I am simulating a complex dynamical system with DifferentialEquations.jl and via callbacks I introduce perturbations of some parameters. I would like to introduce a callback which continuously sets a variable to a constant value (let’s say 2.0) when this constant value is reached. How can I do it?
I tried to use Discrete and Continuous callbacks, but my results are not satisfying:
-
With DiscreteCallback (see first example below), I manage to set the variable to 2.0 only when the callback is called. In all the other time-steps the variable decreases following its derivative (which is not set to zero!).
-
With ContinuousCallback (see second example below), I do not obtain any good result probably because my condition is never met.
I could manipulate the derivative du in the affect! function with DiscreteCallback and I obtain what I want, but I would not like to do that. I would rather preserve the correct physical equation of my model and introduce a callback which defines all the perturbations.
Moreover, with the DiscreteCallback my variable does not hit 2.0 and so the results is not perfect (see third example below).
Problem:
function f(du, u, p, t)
du[1] = -u[1] * p
end
u0 = [10.0]
p = 1
prob = ODEProblem(f, u0, (0.0, 10.0),p)
Ex. 1 (DiscreteCallback):
condition_d(u, t, integrator) = integrator.u[1] <= 2.0
affect_d!(integrator) = integrator.u[1] = 2.0
cb_d = DiscreteCallback(condition_d, affect_d!)
sol = DifferentialEquations.solve(prob, Tsit5(), callback = cb_d)
plot(sol)
hline!([2.0],line=:dash,color=:red)
Ex. 2 (ContinuousCallback):
condition_c(u, t, integrator) = integrator.u[1]-2.0
affect_c!(integrator) = integrator.u[1] = 2.0
cb_c = ContinuousCallback(condition_c, affect_c!)
sol = DifferentialEquations.solve(prob, Tsit5(), callback = cb_c)
plot(sol)
hline!([2.0],line=:dash,color=:red)
Ex. 3 (DiscreteCallback by changing the derivative):
condition_d(u, t, integrator) = integrator.u[1] <= 2.0
function affect_d!(integrator)
integrator.u[1] = 2.0
integrator.p = 0
end
cb_d = DiscreteCallback(condition_d, affect_d!)
sol = DifferentialEquations.solve(prob, Tsit5(), callback = cb_d)
plot(sol)
hline!([2.0],line=:dash,color=:red)