Optimising Julia ODE model

Viewed 102

I'm currently trying to learn Julia but translating some of my code. Below, I exemplify with what kind of problems I'm usually confronted, i.e. small- to medium-sized systems of ODEs tested with a large battery of inputs and forcing functions. Here, I'm using ModelingToolkit.jl but I'm not sure whether this is the best way.

I'd appreciate any input on how to improve this code.

using DataFrames, DifferentialEquations, ModelingToolkit

# ModelingToolkit
@variables t xc(t) xp(t) u(t);
@parameters kel k12 k21;
D = Differential(t);

# Parameters
p = [kel => 1,
     k12 => 2,
     k21 => 1];

# Initial conditions
x0 = [xc => 0,
      xp => 0];

tspan = (0, 10);

# ODEs
odes = [D(xc) ~ -kel*xc - k12*xc + u + k21*xp,
        D(xp) ~           k12*xc + u - k21*xp];

# Stimulus function
# My function
function myfun(t, dose, duration)
    if t >= 0 && t <= duration
        dose
    else
        0
    end
end
@register myfun(t, dose, duration)

stim_size = [1, 2, 3];
stim_length = [1, 2, 3];

# Loop over stimulations
sol = DataFrame();

for i in 1:length(stim_size)
      for j in 1:length(stim_length)

            # Define ODE
            @named sys_ij = ODESystem([u ~ myfun(t, stim_size[i], stim_length[j]); odes])
            prob_ij = ODEProblem(structural_simplify(sys_ij), x0, tspan, p)
            sol_ij = solve(prob_ij)
      
            # Convert to dataframe and add stimulations
            sol_ij_df = DataFrame(sol_ij)
            sol_ij_df[!, :size] = repeat([stim_size[i]], size(sol_ij_df, 1))
            sol_ij_df[!, :length] = repeat([stim_length[j]], size(sol_ij_df, 1))

            # Combine
            append!(sol, sol_ij_df);
      end
end
0 Answers
Related