Which optimizer to use for SIR Epidemic Model?
20 views (last 30 days)
Show older comments
Hi,
Some background: The SIR compartmental model is used to model the spread of an epidemic. The population is split into 3 bins: Susceptible, Infectious, Recovered, and the transition from S --> I and from I --> R are governed by a set of differential equations. There are two parameters in this system of ODEs: beta (transmission rate) and gamma (recovery rate). I've written a code which discretizes the ODEs and it predicts the number of people in each bin during each timestep (1 day), it runs for a set number of timesteps/days (e.g. 200) and produces a plot with 3 curves showing the evolution of S,I,R numbers throughout the simulation.
I now have some data for S/I/R and want to fit the model to the data by varying the 2 parameters (beta and gamma) and minimizing a cost function (which is just a simple least squares - sum of (predicted - actual)^2 )
Is there a black box optimizer (no functions and no derivatives) I can use? Basically just need something to iterate through 2 arrays of parameters (for example beta = [0.2:0.01:0.4] and similarly for gamma) to minimize the cost function, I've read the documentation on fmincon, fminunc, patternsearch, lsqnonlin etc but am quite lost, seems like alot of re-coding? Also, I intend to expand the model (SEIRD) to have 5 bins, 5 ODEs and 5 parameters so I need something which works well in higher dimensions too.
Any recommendations would be greatly appreciated!
Thanks.
0 Comments
Answers (1)
Bjorn Gustavsson
on 13 Dec 2021
One recommendation that you're not likely to like: The constant transition-probability of recovering/dieing has to be unbiological and should be changed to something more adequate. A constant transition-rate leads to exponential response - which cannot be correct (sure everyone and their aunts use this all over the place but that is not an excuse but rather an indictment on lazy/arrogant mathematicians) which implies that the largest number of infected recover the first day - which seems optimistic, and then the tail is most likely way too long with far too many infected remaining after 2, 4, 8 etc "half-recovery-times". Before you can do a parameter fitting and present the results with a straight back and face you'll have to make the model at least sensibly good.
For fitting parameters to systems of ODEs you can have a look at these links:
In essence once you've written a function that integrates the ODE-system for a set of initial conditions and parameters and calculate the sum-of-squared-residuals you're good to go with any of the optimization-functions.
HTH
5 Comments
Bjorn Gustavsson
on 16 Dec 2021
1, No attention to my comment on the oversimplification of this type of constant-rate SIR-type modelling of biological systems?
2, Write an error-function where you integrate the SIR-model using one or the other of the odeNN-functions for the and calculates the residuals relative to the observed data:
function err = err_of_sir_too_simplified(pars,t_obs,SIR_obs)
SIR0 = pars(1:3); % couldn't be bothered to write this for a SIRD-model
alphabeta = pars(4:5); % if you need that the modification should be obvious.
% Next we model the SIR-evolution from the initial state for the given
% transition-rates:
[t_mod,SIR_mod] = ode45(@(t,SIR) ode_sir_too_simplified(t,SIR,alphabeta),t_obs,SIR0);
% And calculates the sum of the squared residuals...
err = sum(sum((SIR_obs-SIR_mod).^2));
end
Where your SIR-modeling-function ought to look something like this:
function dSIRdt = ode_sir_too_simplified(t,SIR,alphabeta)
S = SIR(1);
I = SIR(2);
R = SIR(3);
alpha = alphabeta(1);
beta = alphabeta(2);
dSIRdt = [-alpha*S*I;
alpha*S*I-beta*I;
beta*I];
end
Then after writing these 2 equations you can run the (pointless due to unbiologicalness - you REALLY should ask your teacher about that. If you're paid for this then just: NO.) parameter fitting with any of the general minimization-functions, for example fminsearch:
SIR0 = [12356,3432,12]; % Adjust this to what fits your population estimates
alphabeta = [0.03,0.1]; % These are your transition-rate-guesses
load T_obs.mat
load SIR_obs.mat % You'll have to do something...
par0 = [SIR0,alphabeta]; % Initial parameters for the fitting:
par_est = fminsearch(@(par) err_of_sir_too_simplified(par,T_obs,SIR_obs),par0);
% That should give you a fit for the initial conditions and the
% transfer-rates that best fits the simplified SIR-model to the
% observations.
SIR0_est = par_est(1:3);
alphabeta_est = par_est(4:5);
[t_mod,SIR_mod] = ode45(@(t,SIR) ode_sir_too_simplified(t,SIR,alphabeta_est),T_obs,SIR0_est);
plot(t_obs,SIR_mod)
hold on
plot(t_obs,SIR_obs,'*')
HTH
See Also
Categories
Find more on Surrogate Optimization in Help Center and File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!