This project has two tasks. For Task 1, you are going to write and evaluate for loops that will print out different number sequences. For Task 2, you are going to write functions with for loops, and set up accumulator patterns to add up the number sequences generated by the for loops.
You are to do this project individually.
We have provided for you a template file. After you have finished writing and evaluating your for loops, please cut and paste them along with the sequences of number printed (your input and output) underneath the corresponding questions (Task 1, questions 1 - 5) in the template.
We call this task "twelve days of Christmas"; consider the following traditional Christmas song:
On the first day of Christmas
My true love gave to me
A partridge in a pear tree.
On the second day of Christmas
My true love gave to me
Two turtle doves
And a partridge in a pear tree.
On the third day of Christmas
My true love gave to me
Three French hens,
Two turtle doves,
And a partridge in a pear tree.
And so on, through the twelfth day of Christmas. Let's count a partridge in a pear tree as constituting a single present, so that on the first day, my true love gave me one present. Similarly on the second day my true love gave me three presents, on the third day six presents, and so on.
If I wanted to figure out how many presents I received on a particular day, the most straightforward approach would be to add them all up. Section 1.4 in our textbook explains a slicker approach based on visualizing the presents that day as arranged in a triangle. The triangle can fit together with another equal-sized triangle to form a rectangle. This allows a direct calculation of the number of presents on day n as n(n+1)/2. If all is well, both approaches ought to give the same answers.
Suppose we instead want to figure out my total haul for the entire Christmas season. Added up over all twelve days, how many presents did my true love give me? The geometric approach still works, if you can visualize three-dimensional shapes well enough. You can lay down the big triangle from day 12, stack on top of it a smaller triangle from day 11, and so forth on up to form a pyramid. If you figure out how many of those pyramids fit together to form a rectangular solid, and how long each of the three sides of the rectangular solid are, you can derive a formula for the total number of presents. But I don't recommend you try this, at least without having a more straightforward calculation to check your work against, because most humans aren't very good at rotating pyramids around in their heads. So let's write a straightforward program that totals up the answer. While we're at it, we can compare the two approaches in the single-day case as well.
Here is what you need to do for this task:
Open up a new file window in IDLE and type in a definition for a function, presentsOnDay
. The function
should have one parameter, specifying which day of Christmas you are interested in. (For example, you would pass
in 12 to find out how many presents my true love gave me on the 12th day of Christmas.) Be sure to use a descriptive
name for the parameter. Your function should return the overall number of presents for the specified day. Use the
accumulator pattern to calculate the answer by adding up all the different kinds of presents. Save your program in
a file called xmas.py
.
Use IDLE's "Run Module" command from the Run menu, or equivalently press the F5 key. If IDLE reports any syntax
errors in your program, fix them. When you get past that hurdle, use the Python shell window of IDLE to try your
presentsOnDay
function out for days 1, 2, and 3. Make sure your function gives the same answers as
the ones previously mentioned; if not, fix it. Once you are confident that the function is working, find out how many
presents are on day 12 (write it down).
Add a second function in the same file, this one called presentsThroughDay
. It should again have a
single parameter, this time indicating the last day number you are interested in. For example, if you passed in
the number 12, it would indicate that you were interested in all days up to and including day 12. The function should
return the total number of presents, added up across all the days. You should again use the accumulator pattern to do this.
Each time your function needs to find the number of presents on a particular day, it should
use presentsOnDay
.
Make sure your presentsThroughDay
function produces the right answers if you ask it about just the
first day, or the first two days, or the first three days. Fix any errors you discover. Then find out the total
number of presents my true love gave me over the full 12-day Christmas season (write it down).
One question about an algorithm is whether it produces the correct result. But another question is how well it
scales up to larger problem sizes. My true love actually is generous enough to give me presents even outside
the Christmas season. Get a sense for how well the straightforward algorithm using two accumulations can accommodate
this by trying presentsThroughDay
out with values such as 10, 100, and 1000. (For
example, my parents have been married for over 12775 days.) How far do you have the
patience to go? If a computation is taking too long, you can stop it using the control-c key combination.
In the xmas.py
file window, select your presentsOnDay
function definition by dragging
the mouse through it. Then use the "Comment Out Region" command from the Format menu, or equivalently the
control-3 key combination. This should put ##
characters at the beginning of each line. In
Python, anything from a #
character to the end of the line is a "comment," that is, not an actual
part of the program that will get run. So effectively you have removed this function definition by turning it
into nothing but comments. The advantage is that it is still visible and can be uncommented if you ever want
it back. Now add the following definition to the file:
def presentsOnDay(day): return day*(day+1)//2
Now if you go back to trying presentsThroughDay
with large numbers of days, you should find that
it scales up much better but still gives the same answers . With the new version, how large a number of days do
you have patience for?
Finally, in the template file we have provided for you, write down the following under the corresponding question (Task 2, questions 7):
You will be submitting your code using Moodle; click on the following link for instructions on submitting code using Moodle. For this project, you will need to submit the following 2 files (with the following recommended names):
You will earn one point for each of the following accomplishments:
You wrote a for loop that provided the correct output for Task 1 question 1.
You wrote a for loop that provided the correct output for Task 1 question 2.
You wrote a for loop that provided the correct output for Task 1 question 3.
You wrote a for loop that provided the correct output for Task 1 question 4.
You wrote a for loop that provided the correct output for Task 1 question 5.
You have written a correct contract and docstring for the presentsOnDay
function.
Your presentsOnDay
function uses the accumulator pattern to calculate its answer.
Your presentsOnDay
function returns an answer. Your presentsOnDay
function calculates the correct answer.
(Under Task 2, questions 7 in the template) You stated the number of presents for day 12.
You have written a correct contract and docstring for the presentsThroughDay
function.
Your presentsThroughDay
function uses the accumulator pattern to calculate its answer.
Your presentsThroughDay
function uses the presentsOnDay
function.
Your presentsThroughDay
function returns an answer. Your presentsThroughDay
function calculates the correct answer.
(Under Task 2, questions 7 in the template) You stated the total number of presents through day 12.
All variable and parameter names in your functions are descriptive.
(Under Task 2, questions 7 in the template) Your paragraph explains what function has two different versions. Your paragraph reports on whether the two algorithms computed the same answers in the cases where you tested both.
(Under Task 2, questions 7 in the template) Your paragraph makes it clear whether you compared the two versions directly, or in the context of their use by some other function. (In the latter case, you make clear which other function.)
(Under Task 2, questions 7 in the template) Your paragraph indicates in a general way how the speeds compared. For example, you might say "I didn't notice any difference for parameter values up to ..., but by the time I got to ..., ... was taking several seconds whereas ....."
(Under Task 2, questions 7 in the template) Your paragraph gives the largest value you were willing to wait for with the slow algorithm and approximately how long it took. (Seconds? Minutes? Tens of minutes?)
(Under Task 2, questions 7 in the template) Your paragraph gives the largest value you were willing to wait for with the fast algorithm and approximately how long it took. (Seconds? Minutes? Tens of minutes?)