@@ -29,68 +29,60 @@ the state of host population can also be represented as a vector
2929by concatenating the state of each component of host ` u = vcat(S, vec(I), vec(R)) ` ,
3030where ` S ` is a vector of length ` n ` and ` I ` , ` R ` are matrixes of size ` n × m ` .
3131However, in evolutionary biology,
32- the "mutation" and "extinction" will change the types of " hosts" and " viruses" ,
32+ the "mutation" and "extinction" will change the types of hosts and viruses,
3333which means the ` n ` and ` m ` changes during the evolution,
3434and the length of the state vector ` u ` will also change.
3535
3636## How to use?
3737
38- Similarly to ` DifferentialEquations.jl ` ,
39- you must define reactions firstly (jump in ` DifferentialEquations.jl ` ),
40- For example, the infect reaction of above SIR model is defined as:
38+ The package [ ` Catalyst.jl ` ] ( https://github.com/SciML/Catalyst.jl ) provides a simple way
39+ to build biochemical reaction for ` DifferentialEquations.jl ` .
40+ Similarly, this package provides a macro ` @reaction_eq ` which generate reaction(s),
41+ with given equation.
4142
43+ For example, the infect reaction of above SIR model with multi-type of viruses can be defined as:
4244``` julia
43- # reaction: S_i + I_ij -> 2I_ij
44- @cfunc infect_c (β, S, I) = β * S' * I # function to calculate the rate of infection
45- @ufunc function infect_u! (ind, S, I) # function to update the state when infection happens
46- # ind is the index of the reaction selected with weight calculated by `infect_c`
47- S[ind[2 ]] -= 1 # S_j -= 1
48- I[ind] += 1 # I_ij += 1
49- return nothing
50- end
51- infect = Reaction (infect_c, infect_u!)
45+ @reaction_eq infect β S + I[i] --> 2 I[i]
5246```
47+ where ` i ` donates the virus type. The equation ` S + I[i] --> 2I[i] ` means
48+ the an host infected by the virus ` i ` infect a susceptible host with rate ` β ` ,
49+ then convert the the susceptible host to a infectious host.
50+ This expression will not only generate one reaction but a group of reactions trough the index ` i ` .
5351
54- where ` @cfunc ` is a macro to help you define a function to calculate the rate of reaction,
55- ` @ufunc ` is a macro to help you define a function to update the state when reaction happens.
56- Unlike ` DifferentialEquations.jl ` , the "calculate" function returns an array of rates,
57- which allows variable length state and contains a lot sub-reactions.
58- Additionally, the "update" function accepts a special argument ` ind ` ,
59- which tells you which sub-reaction is selected and should always be the first argument.
60- All of these is designed to work with variable length state.
61-
62- Besides, there is another macro ` @reaction ` helps you define a reaction more easily.
63- The below code is equivalent to the above code:
64-
52+ However, the mutation and extinction can not be defined easily by the macro ` @reaction_eq ` currently.
53+ Thus the alternative macro ` @reaction ` provides a low-level way to build reaction(s)
6554``` julia
66- @reaction infect begin
67- β * S ' * I
55+ @reaction mutation begin
56+ @quickloop μ * I[i]
6857 begin
69- S[ind[2 ]] -= 1
70- I[ind] += 1
58+ i = ind[1 ]
59+ I[i] -= 1 # the host individual is converted to another type
60+ push! (I, 1 ) # add a new type of infectious host to the system
61+ push! (α, randn () + α[i]) # the virulence of the new host type is generated randomly with mean `α[i]`
7162 end
7263end
7364```
65+ This expression defined mutation of virus which contains two parts:
66+ 1 . The ` @quickloop μ * I[i] ` defines how to calculate the rate of mutation,
67+ 2 . The ` begin ... end ` block defines what happens when the host is mutated,
68+ where ` ind ` is a preserved variable which is used to store the index of the mutated host.
7469
7570Once you have defined all reactions, put them together as a tuple:
76-
7771``` julia
78- reactions = (infect, ... )
72+ reactions = (infect, mutation, ... )
7973```
80-
8174and define the initial state and parameters of the system as a named tuple:
82-
8375``` julia
84- params = (β = 0.1 , ... , S = [ 100 ] , I = [1 ;; ], R = [0 ;;]) # the [1;;] syntax requires Julia >= 1.7
76+ params = (β = 0.1 , μ = 0.001 , ... , S = scalar ( 100 ) , I = [1 ], R = [0 ], α = [ 0.5 ])
8577```
78+ where the ` scalar ` will create a type similar to ` Number ` ,
79+ but it can be update in-place like ` Ref ` like ` S[] += 1 ` .
8680
87- Then, you can use ` gillespie ` to simulate the system:
88-
81+ Once reaction and parameters is defined, you can use ` gillespie ` to simulate the system:
8982``` julia
9083max_time = 100 # the maximum time of simulation
9184params′, t, term = gillespie (max_time, params, reactions)
9285```
93-
9486where the ` gillespie ` function returns an tuple ` t, ps′, term `
9587where ` t ` is the time when the simulation ends, ` params′ ` is an updated ` params ` ,
9688and ` term ` is a flag indicating whether the simulation is finished after the maximum time
@@ -102,15 +94,13 @@ but you can use my another package `RecordedArrays` to record them, like this:
10294``` julia
10395using RecordedArrays
10496c = DiscreteClock (max_time) # clock store information of max_time
105- S = recorded (DynamicEntry, c, [100 ]) # create a recorded vector as S with the clock c
106- I = recorded (DynamicEntry, c, [1 ;;]) # create a recorded matrix as I with the clock c
107- R = recorded (DynamicEntry, c, [0 ;;]) # create a recorded matrix as R with the clock c
108- params = (; β = 0.1 , ... , S, I, R) # create new params with recorded S, I, R
97+ S = recorded (DynamicEntry, c, 100 ) # create a recorded number as S with the clock c
98+ I = recorded (DynamicEntry, c, [1 ]) # create a recorded vector as I with the clock c
99+ R = recorded (DynamicEntry, c, [0 ]) # create a recorded vector as R with the clock c
100+ α = recorded (StaticEntry, c, [0.5 ]) # create a recorded vector as α with the clock c
101+ params = (; β = 0.1 , μ = 0.001 , ... , S, I, R, α) # create new params with recorded S, I, R, α
109102gillespie (c, params, reactions) # run the simulation with the clock and new params
110103```
111104
112105More information about ` RecordedArrays ` , see its
113106[ documentation] ( https://wangl-cc.github.io/RecordedArrays.jl/dev ) .
114-
115- Examples and references of this package can be found in
116- [ documentation] ( https://wangl-cc.github.io/EvolutionaryModelingTools.jl/dev ) .
0 commit comments