# How to change specific parameter in DifferentialEquations CallbackSet?

Hello,
I am trying to run a simulation of a bacterial population with Julia. I set a function that takes one parameter (growth rate, mu) that should change at a specific time point (t_in). I set the CallbackSet for the DifferentialEquations package, but I don’t think the condition is implemented because nothing happens to the simulation – the growth does not show any difference. This might be due to the data themselves, but I think I got the syntax wrong.
The CallbackSet was designed to change the amounts of the bacteria, thus, the u parameter. Now I need to change p parameter and I am not sure if I got it right. I am pasting a snippet of the code for syntax checking. Is it correct?
Thank you

``````function dual_logist!(du, u, p, t)
# parameters
μ = p[:μ]   # bacterial growth rate
...
# ODE
du[1] = (μ[1]*u[1]*ł)  - (δ[1]*u[1]*u[5])  - (ω*u[1])
du[2] = (μ[2]*u[2]*ł)  - (δ[2]*u[2]*u[6])  - (ω*u[2])
...
end

using DifferentialEquations
mu = [mu_0, nu_0]
u0 = ...
tspan = (0, 500)
t_in = 100
...
condition_1(u, t, integrator) = t_in     # time
affect_1!(integrator) = μ[1] = mu_1  # amount
cb1 = ContinuousCallback(condition_1, affect_1!)
condition_2(u, t, integrator) = t_in     # time
affect_2!(integrator) = μ[2] = nu_1  # amount
cb2 = ContinuousCallback(condition_2, affect_2!)
parms = (μ=mu...)
conditions = CallbackSet(cb1, cb2)
prob = ODEProblem(dual_logist!, u0, tspan, parms)
soln = solve(prob, Rosenbrock23(), callback=conditions, tstops=[t_in])
``````

Try integrator.p

Thank you, I tried with:

``````condition_1(u, t, integrator) = t_in
affect_1!(integrator.p) = μ[1] = mu_1
cb1 = ContinuousCallback(condition_1, affect_1!)
...
soln = solve(prob, Rosenbrock23(), callback=conditions)
``````

but I got the error:
`syntax: "integrator.p" is not a valid function argument`
So I tried with:

``````affect_1!(p) = μ[1] = mu_1  # amount
``````

and it worked. But I still do not see any difference. To check if a modification is introduced, I set mu_1 to zero. Is the syntax correct?

Oops, sorry, I mean:

`affect_1!(integrator) = integrator.p[:μ] = mu_1` (If the `p` is mutable)

or

`affect_1!(integrator) = integrator.p = a_new_p_with_mu_1_updated ` (If the `p` is immutable)

I’m not sure about the structure of `p`. Could it be a `NamedTuple` or a `LabelledArray`?

Thank you, it is a named tuple:

``````julia> typeof(parms)
NamedTuple{(:μ, :κ, :ω, :δ, :η, :β, :λ), Tuple{Vector{Float64}, Float64, Int64, Vararg{Vector{Float64}, 4}}}
``````

How to create a new NamedTuple based on the old one

``````nt = (a=1, b=2, c=3)

newnt = merge(nt, (; b=10))  #(a=1,b=10,c=3)
``````

EDIT: I noticed `p.μ` is an array, so this might work

``````function affect_1!(integrator)
integrator.p.μ[1] = mu_1
end
``````

Or, if you don’t want side effects of mutating the array:

``````function affect_1!(integrator)
# Copy the array and assign a new value at the 1st element
newμ = replace(integrator.p.μ, 1 => mu_1)
# Replace the old params with the new ones
integrator.p = merge(integrator.p, (; μ=newμ ))
end
``````

Since your parameter set has two tiers, I would like to recommend the package ComponentArrays.jl, which handles nested named components better.

I tried with this approach, but again there was no difference in the data…

Thanks to a tip from Steffen P. it turned out the problem was in the time condition: it should be

``````condition_1(u, t, integrator) = t - t_in
``````

Now it works as you indicated.
Thank you for the support.