Tutorials

Step-by-step tutorials

We present a number of step-by-step tutorials to help you get to know the Simile visual modelling environment.

The first tutorial introduces you to basic Simile techniques. You should work through it before trying the others, since they generally assume that you have done this. The remaining tutorials can be tackled in any order, depending on your interests.

Name Description Author Level Simile topics PDF
Bank account Introduction to basic operations involved in building and running a Simile model Robert Muetzelfeldt 0 Editing model diagram
Building the model
Setting up output displays
Running the model
Saving and loading models
English
Espanol
Predator-prey Classic model of predator-prey dynamics, with some modifications to improve biological realism Robert Muetzelfeldt 1 Multiple-compartment models
Sketch-graph relationships
English
Trees Individual-based modelling of the growth and population dynamics of a stand of trees Robert Muetzelfeldt 1 Working with submodels Population submodel
Customised displays
English

 

Modelling predator-prey interactions

Introduction

The classic, textbook predator-prey model is that proposed by Lotka and Volterra in 1927. In words, the model states that:

  • Each prey gives rise to a constant number of offspring per year;
    In other words, there are no other factors limiting prey population growth apart from predation.
  • Each predator eats a constant proportion of the prey population per year;
    In other words, doubling the prey population will double the number eaten per predator, regardless of how big the prey population is.
  • Predator reproduction is directly proportional to prey consumed;
    Another way of expressing this is that a certain number of prey consumed results in one new predator; or that one prey consumed produces some fraction of a new predator.
  • A constant proportion of the predator population dies per year.
    In other words, the predator death rate is independent of the amount of food available.

Mathematically, the model is conventionally expressed as:

dX/dt = aX - bXY
dY/dt = cbXY - dY

where:

X = size of the prey population (set to an initial value of 5000 in this tutorial);
Y = size of the predator population (45);
a = number of offspring per prey per year (set to 0.5 in this tutorial);
b = proportion of the prey population consumed by one predator per year (0.01);
c = conversion of one prey consumed into new predators (0.01, i.e. 100 rabbits eaten gives rise to one new fox);
d = proportion of predator population dying per year (0.2).

At the end of this tutorial, we will see how to implement the conventional form of the model, exactly as given. However, we will begin by building up a population model for a single species in System Dynamics terms, then add the predator population, then show how one of the relationships can be made more biologically realistic, before returning to the conventional form of the model.

Page type: 

Stage 1: Modelling the dynamics of a single population

Step 1
Add two  compartments to the desktop, and rename them rabbits and foxes
Step 2
Draw a  flow into the rabbits compartment, and rename it rabbit repro
Step 3
Draw a  flow out of the rabbits compartment, and rename it predation
Step 4
Draw an influence arrow from:
  • the rabbits compartment to the rabbit repro flow;
  • the rabbits compartment to the predation flow;
  • the foxes compartment to the predation flow;

Your model diagram should now look like this:

Step 5
Enter the following expression for the rabbit repro flow: 0.5*rabbits
Step 6
Enter the following expression for the predation flow: 0.01*rabbits*foxes
Step 7
Set the initial value for the rabbits compartment to 5000
Step 8
Set the initial value for the foxes compartment to 45
Step 9
“Build” the model.
Step 10
Change the Run Control settings:
  • Set to 50
  • Set to 0.1
Step 11
Set up a plotter display for the rabbits compartment.
Step 12
Run the model

Note that the population grows exponentially — there is nothing to hold it in check.

Stage 2: Adding in predator dynamics

Step 1
Add a  flow into the foxes compartment, and rename it fox repro.
Step 2
Add a  flow out of the foxes compartment, and rename it fox mortality.
Step 3
Draw an  influence from the rabbit’s predation flow to the fox repro flow.

This reflects the assumption in the standard textbook model, that the predator reproduction is proportional to rate of predation on the prey.

Your model diagram should now look like this:

Step 4
Enter the following expression for the fox repro flow: 0.01*predation
Step 5
Enter the following expression for the fox mortality flow: 0.2*foxes
Step 6
Rebuild the model
Step 7
Set up  graph display for the foxes compartment

Note that you need to have a separate plotter display, since the number of foxes is typically a couple of orders of magnitude less than the number of rabbits. If you plotted them on the same graph, the graph line for the number of foxes would be right on the X axis.

Step 8
Run the model again

You should now see that the rabbits and the foxes compartments cycle, with the rabbits population crashing as the foxes population increases, followed by a crash in the foxes population.

Stage 3: Re-casting the model diagram

The present model is based on a number of assumptions that are biologically unsound. For example, it assumes that the number of rabbits eaten per fox is directly proportional to the number of rabbits, so doubling the number of rabbits doubles the number eaten per fox — even if there are millions of rabbits around!

We will tackle the problem of making the model more biologically realistic in two stages. First, we will change the model diagram a little, adding in a couple of variables and changing the influence arrows, but retaining the same mathematical structure: the revised model should produce exactly the same results. These changes provide more appropriate handles in our model for expressing biologically-meaningful relationships. Then, in the following stage, we will replace some of the simplistic assumptions in this model with others that are biologically more realistic.

Step 1
Use the  delete tool to remove the influence arrows from rabbits to predation, and from predation to fox repro.
Step 2
Add in two new  variables, naming them rfox and eaten per fox.
Step 3
Draw  influence arrows:
  • from the rabbits compartment to eaten per fox;
  • from eaten per fox to rfox;
  • from eaten per fox to the predation flow;
  • from rfox to the fox repro flow; and
  • from the foxes compartment to the fox repro flow.

Your model diagram should now look like this:

Step 4
Enter the following expression for each variable or flow:
  • eaten per fox : 0.01*rabbits
  • rfox : 0.01*eaten_per_fox
  • predation : eaten_per_fox*foxes
  • fox repro : rfox*foxes

Satisfy yourself that these changes have not altered the mathematical nature of the model.

Step 5
Re-build and run the model again, confirming that you do indeed get the same behaviour that you had before.

Stage 4: Sketching biologically meaningful relationships

What we now have are some variables in our model ( and ) for introducing biologically-meaningful relationships. The influence arrows we have drawn to these two variables expresses the biologically-reasonable assumptions that:

  • the number of rabbits eaten per fox, , depends on the number of rabbits; and
  • the number of baby foxes produced per fox, , depends on the number rabbits eaten per fox.

So far, however, we have retained the simplistic assumptions from the conventional model: we have asumed that the number of rabbits eaten per fox is directly proportional to the number of rabbits; and that the rate of reproduction per fox is directly proportional to the number of rabbits eaten. In reality, both assumptions are way off the mark: if there are lots of rabbits around, then foxes reach a limit of how many they can eat. Similarly, even if foxes succeed in eating many rabbits, there is an upper limit to the number of offspring they can produce per year.

How can we incorporate these refinements?

We have two options. One is to find some mathematical expression that better captures our understanding. If you are mathematically inclined, you might like to give that a try. The other is to exploit Simile’s ability to draw a sketch graph of any relationship between two variables, and that’s what we’ll do here.

Step 1
Open up the Equation dialogue window for the variable eaten per fox, and delete the existing expression.
Step 2
Click on the  graph button

This opens up a separate graph pad window.

The scaling for each axis is determined by the Xmin, Xmax and Ymin, Ymax edit boxes. The graph pad area (initially a horizontal line running through the middle of the graph pad) which can be adjusted up and down using the mouse.

Step 3
Scale the X axis (representing number of rabbits), by entering a value of 10000 in the Xmax edit box at the right of the X axis.
Step 4
Scale the Y axis (number of rabbits eaten per fox per year), by entering a value of 100 in the edit box at the top of the y axis.
Step 5
Move the mouse into the graphpad area, and move the mouse around while holding down the mouse button.

Notice how you can adjust the position of the line showing the relationship between the Y and X axes.

Step 6
Adjust it so that it passes through the origin at (0,0), and rises up smoothly till it reaches a plateau (asymptotic) value, looking something like this:

When Simile comes to run the model, it will use linear interpolation to work out what the value on the Y axis is knowing the value on the X axis.

Step 7
Click on the Enter button to close the sketch graph window.
Step 8
In the main Equation window, Simile has entered the text graph( ) into the equation field. Insert the name of the rabbits compartment between the brackets, so that the expression now read: graph(rabbits)
Step 9
Open up a graph pad in the Equation dialogue window for the variable rfox, and delete the existing expression.

We are now going to sketch the relationship between , the number of foxes produced per fox per year, and , the number of rabbits eaten per fox per year.

Step 10
Scale it, setting Xmax to 100 and Ymax to 1.

Note that the Xmax value (100) is the same as the Ymax value in the previous sketch graph. This is because they actually refer to the same variable: number of rabbits eaten per fox per year. The value of 1 for the Y axis indicates that foxes cannot produce more than 2 baby foxes per year.

Step 11
Sketch a graph looking something like this:

Before reading the rest of this comment, try to figure out for yourself what this is saying... It shows that a fox does not reproduce at all when its food intake is below some lower threshold. After that, its rate of reproduction is directly proportional to the amount of additional food consumed, up to some maximum, plateau level: the maximum number of young it can produce per year.

Step 12
Click on the Enter button to close the sketch graph window.
Step 13
Edit the expression so that it reads graph(eaten_per_fox).

Note that the variable whose label is (with spaces between the words) is written as eaten_per_fox in the equation. This is because some characters which are allowed in labels are not allowed in variables in expressions. Note that Simile always lists the influencing variables at the bottomof the Equation window, so you can always check on what spelling it’s using.

Step 14
Rebuild the model, and run it again.

You should notice a difference in the shape of the graphs, reflecting the changes in the model.

Stage 5: Bonus section: re-visiting the classic predator-prey model.

In this tutorial, I began by sticking faithfully to the mathematical form of the traditional Lotka-Volterra predator-prey model, but I designed the System Dynamics diagram to put more emphasis on biological processes. Thus, I used four flow arrows, representing reproduction and mortality processes for the two populations, even though these were not explicitly mentioned in the original model: all we had were two rate-of-change equations. This reflects my personal attitude to modelling, that it should begin as a conceptual design activity, rather than being driven by mathematical notation.

Nevertheless, there will be times when you come across a model expressed as a set of differential equations, and you feel you have neither the inclination nor ability to re-express it in terms of biological process, represented as separate flows. What can you do?

Well, it’s really pretty straightforward All you have to do is to follow these four simple steps:

  • Create one compartment for each state variable
  • Make a single inflow for each compartment
  • Draw influence arrows from compartments to inflows, as required by the differential equations.
  • Enter each differential equation into the flow for the corresponding state variable

Let’s see this in action:

Step 1
Start a new model.
Step 2
Add two compartments, and re-label them X and Y respectively.
Step 3
Add a single flow into each compartment, and re-label them dXdt and dYdt respectively.
Step 4
Draw influence arrows from both compartments to both flows (i.e. four arrows in total).

Your model diagram should now look like this:

Step 5
Enter the following expressions into the flows:
  • dXdt : 0.5*X - 0.01*X*Y
  • dYdt : 0.01*0.01*X*Y - 0.2*Y
Step 6
Build and run the model!

Individual-based modelling of a population of trees

Introduction

The main aim of this tutorial is to introduce you to individual-based modelling.

System Dynamics (or “compartment-flow”) modelling generally does not represent individuals in a population. Instead, all the individuals are lumped together and represented by a single value: the number of individuals in a population, the total weight of all the individuals, or the total amount of some substance they contain (water, carbon or nitrogen, for example).

However, there are many situations when it is important to represent each individual in the population separately. For example, the behaviour of the whole population may be partly a product of interactions between individuals, or between individuals and their environment.

In this tutorial, we will look at how to model a population in terms of a set of individuals — in this case, trees. We will not consider how to handle interactions. Another tutorial, involving the modelling of the interaction between trees and crops, will be available shortly. However, we will see how to specify a set of individuals, how to give them individual behaviour (growth), and how to represent the creation of new trees and the death of existing ones.

Stage 1: Modelling the growth of a single tree

Step 1
Add a compartment to the desktop, and rename it size.
Step 2
Draw a flow into the size compartment, and rename it growth.
Step 3
Add a variable to the desktop, above the growth flow, and rename it gr.

The variable gr represents the maximum rate of growth of the tree.

Step 4
Draw an influence arrow from both the size compartment and the gr to the growth flow.

Your model diagram should now look like this:

Step 5
Enter the following expression for the growth flow: gr*(1-size/25)

In this expression, the value 25 is the maximum size the tree will reach. It’s growth rate will fall from the maximum given by gr at the start of the simulation. This form of mathematical expression is a convenient way of achieving this desired behaviour of rapid initial growth reducing as the final maximum size is reached.

Step 6
Set the initial value for the size compartment to 3.
Step 7
Set the value for the variable gr to 0.2.
Step 8
Prepare the model for running.
Step 9
Set up a plotter display helper for the size compartment
Step 10
Run the model

Stage 2: Extending the model to represent a population of trees

Step 1
Draw a submodel box to completely enclose your model diagram.
  • Click on the  submodel tool on the toolbar
  • Move the mouse to the top left of your model diagram
  • Drag the mouse (i.e. depress the mouse button and move the mouse) to the bottom-right of your model diagram
  • Release the mouse button
Step 2
Rename the submodel tree.

This submodel will represent a population of trees. However, rather than calling it “trees”, it is conventional to name the class of objects after one individual, so here we call it “tree”.

Step 3
Open up the submodel Properties dialogue window.
  • Choose the  select tool
  • Double-click anywhere inside the submodel
Step 4
Click the radio button labelled “Using population symbols”.
Step 5
Choose a nice background colour for the submodel.
Step 6
Close the submodel properties dialogue window.

Your model diagram should now look like this:

Note that the submodel boundary now has an extra line on the top-and-left, and on the bottom-and-right. This is a visual signal that Simile now represents this as a “population submodel”.

Step 7
Change the expression for gr from its current value (0.2) to rand_const(0.1,0.3).

Since we will now be simulating the growth of several trees, we are giving each one a different growth rate, randomly selected between 0.1 and 0.3. This could reflect, for example, differences in the soil conditions where each tree grows, or genetic differences between trees.

Step 8
Add a  creation symbol to the model diagram, and give it a value of 5.

This is used to specify the initial number of trees (i.e the number at time zero). If we didn’t put this into our model, then our population would start off empty, i.e. with no trees.

Step 9
Add an  immigration symbol to the model diagram, and give it a value of 2.

We are stating that two new trees are created every year.

Step 10
Add a  loss symbol to the model diagram.
Step 11
Rename the loss symbol death.
Step 12
Draw an influence arrow from the compartment size to this symbol.

Your model diagram should now look like this:

Step 13
Enter the expression size>17 for the symbol labelled death.

This states that a tree will “die” (be eliminated from the model) when its size exceeds 17.

Step 14
Rebuild the model, and run it again.

You should see multiple lines on the graph. Each line represents the growth of a single tree. Note that each line has a different slope, since each tree has a randomly different growth rate (as determined by the variable gr). Note also that each year two new trees are created, and that trees disappear when their size value exceeds 17.

Stage 3: Calculating aggregate information

Step 1
Add a variable outside the tree submodel, and rename it total.
Step 2
Draw an influence arrow from the compartment size inside the tree submodel to the variable total.

Your model diagram should now look like this:

Notice how the influence arrow crosses the submodel boundary.

Step 3
Enter the expression sum({size}) for the variable total.

Be very careful to get the brackets right. The outer (round) brackets enclose the argument for the built-in function sum( ), which can find the total value of an array of a list. In this case, we want the sum( ) function to find the total value of a list of size values, one for each tree. It’s a “list” rather than an “array” of values, because the number of trees (and hence the number of values to be summed) is not fixed, but changes over time. Simile uses braces {....} to denote a list, and square brackets [....] to denote an array.

Step 4
Re-build the model.
Step 5
Call up a plotter display for the variable total.
Step 6
Run the model again

In additional to the plot for the growth of individual trees, you should see a graph with a single line for the total size of all the trees, rising smoothly up, then bouncing around an asymptotic value. Why does it show this behaviour? First, trees are growing and more are being added, with none dying. Later, the growth of existing trees and the addition of new (small) ones is balanced by the sporadic death of big trees. The top of the curve is not smooth because the time it takes for a tree to die depends on its growth rate, which is randomly determined.

Stage 4: Visualising the trees in space

Step 1
Add two variables inside the tree submodel, and rename them x and y.

Step 2
Enter the following expression for the variable x: rand_const(0,50)

We imagine a 1 hectare plot, with the trees on the left-hand side: i.e. their x-coordinate is between 0 and 50 m. The actual x-coordinate for each tree is randomly determined.

Step 3
Enter the following expression for the variable y: rand_const(0,100).

The trees can be anywhere between the front and the back of the 1 hectare plot. Hence, the y-coordinate for each tree is randomly determined between 0 and 100 m.

Step 4
Re-build the model.
Step 5
Call up the lollipop display. When it prompts you for the three variables required to set up the display, click on the variable x, the variable y, and the variable size respectively, in that order.

You should see a gridded area, with five lollipops on it, representing the five trees created at initialisation time.

Step 6
Run the model again.

Now, you can the trees growing, new trees being created, and trees dying off when they reach the threshold height. Note that we have not changed the mathematical nature of the model. All we have done is to change the way we visualise its behaviour — but this has a dramatic effect on our appreciation of what’s going on.