1 Introduction.

The present document has been prepared to illustrate the process of IDM using R to Master of Public Health students at Achutha Menon Centre for Health Science Studies, Sree Chitra Tirunal Institute for Medical Sciences and Technology.

2 Load Library.

Library deSolve and tidyverse has been used in the present document.

3 Framework for mathematical modeling

It is considered as a good practice to draw the model by hand/ by using any computer software for conceptualising the model. Following steps can be considered as minimum framework/ steps required for modelling using R:-

  1. Evidence synthesis
  2. Create input parameters
  3. Create a model using input values
  4. Return a dataframe as output using model equations
  5. Exploratory Data Analysis of the output

4 Illustrative example: Infected Cohort

Let us assume a situation wherein we have a closed cohort of 1000 individuals who are infected as well as infective. The duration of infectiousness will remain for 07 days. Once recovered, they remain immune throughout their lifespan.

4.1 Understanding the model

Infected Cohort Model

Figure 4.1: Infected Cohort Model

4.2 Evidence synthesis

As a pre-requisite to model building, we need to undertake evidence synthesis exercise to extract required parameters from the literature or by conducting a study.

initial_number_infected <- 1000
initial_number_recovered <- 0 
Duration_of_infectiousness <- 7 
recovery_rate <- 1/Duration_of_infectiousness
follow_up_duration <- 30

4.3 Create input parameters.

Once parameters are obtained, they are placed into three major parameter inputs viz initial values for each compartment, transition parameters from one compartment to another, and the time stamps for which modelling is required.

initial_state_values <- c(I = initial_number_infected, 
                          R = initial_number_recovered) 

parameters <- c(gamma = recovery_rate) 
times <- seq(from = 0, to = follow_up_duration, by = 1) 

initial_state_values
##    I    R 
## 1000    0
parameters
##     gamma 
## 0.1428571
times
##  [1]  0  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
## [26] 25 26 27 28 29 30

4.4 Create a model function using input values

The model is created from the above mentioned parameters by specifying differential equations. In R, a function is an object so that the researcher is able to pass control to the function, along with arguments that may be necessary for the function to accomplish the actions. For performing differential equations, we create a function with compartment as well as transition parameter at varied timestamps.

cohort_model <- function(time, state, parameters) {     
   with(as.list(c(state, parameters)), {  
   dI <- -gamma * I
   dR <- gamma * I
   return(list(c(dI, dR)))                             
   })
}

4.5 Return a dataframe as output using model equations

A data frame is constructed by application of the differential model. Herein, Odinary Differential Equations (ode) function takes initial compartment values, timestamps, parameters and the model function as arguments.

output <- as.data.frame(ode(y = initial_state_values, 
                            times = times, 
                            func = cohort_model,
                            parms = parameters))

4.6 Exploratory Data Analysis of the output

knitr::kable(output)
time I R
0 1000.00000 0.0000
1 866.87790 133.1221
2 751.47726 248.5227
3 651.43886 348.5611
4 564.71820 435.2818
5 489.54178 510.4582
6 424.37297 575.6270
7 367.87958 632.1204
8 318.90670 681.0933
9 276.45316 723.5468
10 239.65110 760.3489
11 207.74823 792.2518
12 180.09235 819.9076
13 156.11808 843.8819
14 135.33531 864.6647
15 117.31919 882.6808
16 101.70141 898.2986
17 88.16270 911.8373
18 76.42630 923.5737
19 66.25227 933.7477
20 57.43262 942.5674
21 49.78707 950.2129
22 43.15931 956.8407
23 37.41385 962.5861
24 32.43324 967.5668
25 28.11566 971.8843
26 24.37284 975.6272
27 21.12828 978.8717
28 18.31564 981.6844
29 15.87742 984.1226
30 13.76379 986.2362

Since, more than one column is representing the state of the person (Infected or recovered), we need to transform the data into tidy format. A tidy data format is said to present when each column represents one variable, each row has one observation and each cell has one value.

dat <- output %>% pivot_longer(cols = c(I,R),
                        names_to = "state",
                        values_to = "value")
knitr::kable(head(dat,10))
time state value
0 I 1000.0000
0 R 0.0000
1 I 866.8779
1 R 133.1221
2 I 751.4773
2 R 248.5227
3 I 651.4389
3 R 348.5611
4 I 564.7182
4 R 435.2818

Visualization is a recommended exploratory data analysis method. Let us see how infected and recovered compartments were changing in the model.

dat %>% ggplot(aes(x = time,
                   y = value,
                   color = state,
                   group = state))+
  geom_line()+
  xlab("Time(Days)")+
  ylab("Number of persons")+
  labs(title = "Changes in Infected and Recovered individuals")

Based on the output, at day 03 of follow up, as a Public Health specialist, you are required to provide inputs for logistic planning for the next 28 days. You are required to provide following details:-

  1. How many people in the cohort are likely to recover by end of 4 weeks of follow- up? What is the proportion of people who are likely to be recovered in next 28 days?

  2. If all of them were hospitalized patients, how many people are likely to be present in the hospital after 28 days?

  3. Assuming the disease require intensive care to the extent of one ventilator requirement for every five patients, how many ventilators are required to be functional at 07 days of follow up?

Recovered after 28 days:-

dat$value[dat$time == 28 &
            dat$state == "R"]
## [1] 981.6844

Proportion of cohort recovered:-

(dat$value[dat$time== 28 & dat$state == "R"]/
  (dat$value[dat$time== 28 & dat$state == "R"] + 
     dat$value[dat$time== 28 & dat$state == "I"]))*100
## [1] 98.16844

Likely to be in the hospital after 28 days:-

dat$value[dat$time == 28 &
            dat$state == "I"]
## [1] 18.31564

Ventilators required at 7 days:-

(dat$value[dat$time == 7 &
            dat$state == "I"])/5
## [1] 73.57592