Goals

In this project, you will make a calculator that determines the population size of foxes and rabbits who live within a certain area of land, as that number changes from year to year.

Image of a fox and rabbits.

Photo Credit: Duncan Monk (CC BY-NC-ND)

You will be practicing the following concepts from prior labs:


Summary

In many environments, two or more species compete for the available resources. Classic predator–prey equations have been used to simulate or predict the dynamics of biological systems in which two species interact, one as a predator and the other as prey. You will use a simplified version of the Lotka-Volterra equations for modeling fox/rabbit populations, described below.

Let the following variables be defined as:
$r_t$
The number of prey (rabbits) at time $t$.
$f_t$
The number of predators (foxes) at time $t$.
$\alpha$
The birth rate of prey.
$\beta$
The death rate of prey (depends on predator population).
$\gamma$
The birth rate of predators (depends on prey population).
$\delta$
The death rate of predators.

Then, we can define the populations of the next time period ($t+1$) using the folowing system of equations:

$$\begin{eqnarray} r_{t+1} & = & r_{t} &+& \alpha \cdot r_{t} &-& \beta \cdot r_t \cdot f_t \\ & = & \textrm{rabbits} &+& \textrm{rbirths} &-& \textrm{rdeaths} \\ \\ f_{t+1} & = & f_{t} &+& \gamma \cdot f_{t} \cdot r_{t} &-& \delta \cdot f_t\\ & = & \textrm{foxes} &+& \textrm{fbirths} &-& \textrm{fdeaths} \\ \end{eqnarray}$$

You will write a program that prompts the user for the parameters of the simulation, outputs the population sizes for the simulated period, and then ouputs some final summary statistics. This calculator will be built in stages: Checkpoint A, Checkpoint B, and then Final Code. There is a demo associated with each intermediate stage.

Part of this project is an exercise in having control over functions and patterns to produce target outputs. It is not a creative exercise, but rather the opportunity for you to demonstrate precision, control and being detail-oriented. You are asked to demonstrate the requested behavior and output, matching the sample output exactly. In all samples below, user input is shown in italics and underlined.

Due Dates


Checkpoint A

For Checkpoint A, you will need to demonstrate a program that does the following:

  1. Prompts the user for the parameters of the model: $\alpha, \beta, \gamma, \delta$. For Checkpoint A, you can assume that the user always enters a non-negative float (greater than or equal to zero) for each.
  2. Prompts the user to enter the initial values of the populations, $r_0, f_0$, representing thousands of animals. For Checkpoint A, for these you can assume that the user always enters a non-negative decimal value (greater than or equal to zero) with three or fewer decimal places.
  3. Prompts the user for the timescale of the simulation. For Checkpoint A, you can assume that the user always enters a non-negative integer (greater than or equal to zero).
  4. Calculates and prints the populations of the rabbits and foxes for each time period of the simulation. Since the populations are expressed in the thousands, the calculated values should be rounded to three places.
  5. Matches the sample input/output below.

    The spacing will be checked. You can use an online "Visual Diff" checker to analyze how your output compares to the given output. Just copy-paste the given sample on one side and your program's output on the other, to easily compare spacing, etc.

  6. Demo. Demo Checkpoint A.

Sample Input/Output

Sample 1
==> Rabbits and Foxes Population Simulator <==

--- Model Parameters ---
Rabbits birth rate: 1
Rabbits death rate: 0
Foxes birth rate: 2
Foxes death rate: 0

--- Initial Population ---
Number of rabbits (in thousands) at t = 0: 5
Number of foxes (in thousands) at t = 0: 5
Timescale: 1

Time t = 0: 5.0k rabbits, 5.0k foxes
Time t = 1: 10.0k rabbits, 55.0k foxes
Sample 2
==> Rabbits and Foxes Population Simulator <==

--- Model Parameters ---
Rabbits birth rate: 0.2
Rabbits death rate: 0.005
Foxes birth rate: 0.001
Foxes death rate: 0.2

--- Initial Population ---
Number of rabbits (in thousands) at t = 0: 100
Number of foxes (in thousands) at t = 0: 10
Timescale: 10

Time t = 0: 100.0k rabbits, 10.0k foxes
Time t = 1: 115.0k rabbits, 9.0k foxes
Time t = 2: 132.825k rabbits, 8.235k foxes
Time t = 3: 153.921k rabbits, 7.682k foxes
Time t = 4: 178.793k rabbits, 7.328k foxes
Time t = 5: 208.001k rabbits, 7.173k foxes
Time t = 6: 242.141k rabbits, 7.23k foxes
Time t = 7: 281.816k rabbits, 7.535k foxes
Time t = 8: 327.562k rabbits, 8.151k foxes
Time t = 9: 379.725k rabbits, 9.191k foxes
Time t = 10: 438.22k rabbits, 10.843k foxes

Advice and Hints

Hint:You will need to round each population value, since we do not have fractional rabbit or fox populations. To round a value to a certain precision, use the round() function. For example, say, you want to round a float called val to three decimal places, then the rounded value can be calculated using: round(val,3). Try it in PythonTutor.


Checkpoint B

For Checkpoint B, you will extend your code from Checkpoint A by supporting handling large death rates and printing summary statistics:

  1. Extend your program to support large death rates. You cannot have negative rabbits or negative foxes, so if the population values are ever negative, consider the population to be zero instead.
  2. After the year-by-year simulation, print a summary report that features: the average rabbit population, the average fox population, the minimum rabbit population, and the maximum fox population.
  3. Matches the sample input/output below, exactly.

  4. Demo. Demo Checkpoint B.

Sample Input/Output

Sample 3
==> Rabbits and Foxes Population Simulator <==

--- Model Parameters ---
Rabbits birth rate: 0.2
Rabbits death rate: 0.005
Foxes birth rate: 0.001
Foxes death rate: 0.2

--- Initial Population ---
Number of rabbits (in thousands) at t = 0: 100
Number of foxes (in thousands) at t = 0: 10
Timescale: 10

Time t = 0: 100.0k rabbits, 10.0k foxes
Time t = 1: 115.0k rabbits, 9.0k foxes
Time t = 2: 132.825k rabbits, 8.235k foxes
Time t = 3: 153.921k rabbits, 7.682k foxes
Time t = 4: 178.793k rabbits, 7.328k foxes
Time t = 5: 208.001k rabbits, 7.173k foxes
Time t = 6: 242.141k rabbits, 7.23k foxes
Time t = 7: 281.816k rabbits, 7.535k foxes
Time t = 8: 327.562k rabbits, 8.151k foxes
Time t = 9: 379.725k rabbits, 9.191k foxes
Time t = 10: 438.22k rabbits, 10.843k foxes

--- Simulation Statistics ---
Average rabbit population: 232.546k
Average fox population: 8.397k
Min rabbit population was 100.0k at t=0
Max fox population was 10.843k at t=10
Sample 4
==> Rabbits and Foxes Population Simulator <==

--- Model Parameters ---
Rabbits birth rate: 0.2
Rabbits death rate: 0.005
Foxes birth rate: 0.001
Foxes death rate: 0.2

--- Initial Population ---
Number of rabbits (in thousands) at t = 0: 700
Number of foxes (in thousands) at t = 0: 350
Timescale: 4

Time t = 0: 700.0k rabbits, 350.0k foxes
Time t = 1: 0.0k rabbits, 525.0k foxes
Time t = 2: 0.0k rabbits, 420.0k foxes
Time t = 3: 0.0k rabbits, 336.0k foxes
Time t = 4: 0.0k rabbits, 268.8k foxes

--- Simulation Statistics ---
Average rabbit population: 140.0k
Average fox population: 379.96k
Min rabbit population was 0.0k at t=1
Max fox population was 525.0k at t=1

Final Code

In your final code, you will extend the above code to handle a few special user-input scenarios:

There is no demo for your final code.

Advice and Hints

Hint: The exit() function in the sys library can be used to halt the program running and report an exit code back to the operating system. Please use exit(-1), which will report it as an error. Here is a little code demonstrating this, but note that it will not run in PythonTutor (which does not let you use the sys library). You will need to copy-paste the code and run it in a different environment.

Sample Input/Output

Sample 5
==> Rabbits and Foxes Population Simulator <==

--- Model Parameters ---
Rabbits birth rate: 0.2
Rabbits death rate: 0.005
Foxes birth rate: 0.001
Foxes death rate: 0.2

--- Initial Population ---
Number of rabbits (in thousands) at t = 0: 100
Number of foxes (in thousands) at t = 0: -10
Timescale: 3

Time t = 0: 100.0k rabbits, 0.0k foxes
Time t = 1: 120.0k rabbits, 0.0k foxes
Time t = 2: 144.0k rabbits, 0.0k foxes
Time t = 3: 172.8k rabbits, 0.0k foxes

--- Simulation Statistics ---
Average rabbit population: 134.2k
Average fox population: 0.0k
Min rabbit population was 100.0k at t=0
Max fox population was 0.0k at t=0
Sample 6
==> Rabbits and Foxes Population Simulator <==

--- Model Parameters ---
Rabbits birth rate: 0.2
Rabbits death rate: 0.005
Foxes birth rate: 0.001
Foxes death rate: 0.2

--- Initial Population ---
Number of rabbits (in thousands) at t = 0: 100
Number of foxes (in thousands) at t = 0: -10
Timescale: -3
Error: cannot have a negative timescale

Extra Credit

You can get extra credit by checking for more error conditions. For example, you could reject user-inputs specifying negative birth rates for foxes (+1) or user-inputs that specify negative death rates for rabbits (+1). You could round user-inputs that specify populations in thousands to three places; for example 1.0006k foxes is 1000.6 foxes, and likely should be rounded to 1.0001k (or 10001) foxes (+1). Your enhancements should not change any of the functionality specified in the assignment.

You will get no more than 10 points total for extra credit. You must describe any extra-credit work in your docstring to get credit: use the phrase "EXTRA CREDIT", explain what error condition you handle, and give a sample input showing the behavior. If you do not describe your extra credit work, it will get ignored.


Grading Rubric

Checkpoints [20%]

Checkpoint demos are each worth 10 points; each is all or nothing.

Programming Design and Style [25%]

In addition to being correct, your program should be easy to understand and well documented. For details, see the rubric below.

Correctness [55%]

The most important part of your grade is the correctness of your final program. Your program will be tested numerous times, using different inputs, to be sure that it meets the specification. You will not get full credit for this unless your output matches the sample output exactly for every case, including capitalization and spacing. Attention to detail will pay off on this assignment. For details, see the rubric below.

Detailed Rubric

Correctness: functional features (50 points -- 5 pts each)

Feature 1 The prompts for user input are in the order specified (Ex: Sample 1) and values in thousands that users enter are rounded to three decimal places before they are used in calculations.
Feature 2: The output for each time t is given, for each time between 0 and the requested timescale entered by the user (Ex: Sample 4).
Feature 3: The output for each time t shows correct fox and rabbit populations, rounded to three decimal places (Ex: Sample 3 and 4).
Feature 4: The output for fox and rabbit populations never grows negative; zero is the smallest population allowed (Ex: Sample 4).
Feature 5: The average rabbit popuation is correctly computed, rounded to three decimal places, and matches the sample output (Ex: Sample 3 and 4).
Feature 6: The average fox popuation is correctly computed, rounded to three decimal places, and matches the sample output (Ex: Sample 3 and 4).
Feature 7: The minimum rabbit popuation is correctly computed, rounded to three decimal places, shows the correct time t in which the minumum population was first encountered, and matches the sample output (Ex: Sample 3 and 4).
Feature 8: The maximum fox popuation is correctly computed, rounded to three decimal places, shows the correct time t in which the minumum population was first encountered, and matches the sample output (Ex: Sample 3 and 4).
Feature 9: When a user enters a negative value for an initial rabbit or fox population, it is treated as zero (Ex: Sample 5).
Feature 10: When a user enters negative values for a timespan, an error message is shown and the program exits with an appropriate exit code signaling an error (Ex: Sample 6).

Correctness: spacing, spelling, grammar, punctuation (5 points)

Your spelling, punctuation, etc. get a separate score: each minor error in spacing, punctuation, or spelling gets a score of 2.5, and each major error gets a score of 5. Here is how the score translates to points on the assignment:

[5]Score = 0
-1 0 < Score <= 2.5
-2 2.5 < Score <= 5
-3 5 < Score <= 7.5
-4 7.5 < Score <= 10
-5Score > 10

Programming Design and Style (25 points)

Docstring (5 points)
There should be a docstring at the top of your submitted file with the following information:
1 pt.Your name (first and last)
1 pt.The course (CS 115)
1 pt.The assignment (e.g., Project 1)
2 pts.A brief description of what the program does
Documentation (6 points)
Not counting the docstring, your program should contain at least three comments explaining aspects of your code that are potentially tricky for a person reading it to understand. You should assume that the person understands what Python syntax means but may not understand why you are doing what you are doing.
6 pts.You have at least 3 useful comments (2 points each)
Variables (5 points)
5 pts.Variables have helpful names that indicate what kind of information they contain.
Algorithm (4 points)
2 pts.Your algorithm is straightforward and easy to follow.
2 pts.Your algorithm is reasonably efficient, with no wasted computation or unused variables.
Program structure (5 points)
All or nothing: your code should define a main function and then call that function, just like our programs do in the lab. Other than library imports, the docstring, and the final call to main(), you should not have any stray code outside a function definition.
Catchall
For students using language features that were not covered in class, up to 5 points may be taken off if the principles of programming style are not adhered to when using these features. If you have any questions about what this means, then ask.

Submission

You should submit your final code on Moodle by the deadline. I strongly encourage you to take precautions to make and manage backups while you work on your project, in case something goes wrong either while working or with your submission to Moodle.

Name the file you submit to Moodle yourlastnameP1.py, substituting your actual last name (in lowercase) for yourlastname.

Late Policies

Project late policies are outlined in the course policies page.

Collaboration Policy

Programming projects must be your own work, and academic misconduct is taken very seriously. You may discuss ideas and approaches with other students and the course staff, but you should work out all details and write up all solutions on your own. The following actions will be penalized as academic dishonesty:

Project collaboration policies are described in the course policies page.

References

This assignment is based on the CS1 "Rabbits & Foxes" assignment by Adam A Smith (University of Pugent Sound), published via NCWIT's EngageCSEdu project.