From 7d0baa014a00fbccdcfb1fd7ca37b262d4090e89 Mon Sep 17 00:00:00 2001 From: John Blischak Date: Sun, 16 Jun 2013 22:26:19 -0500 Subject: [PATCH] Removed extra materials on testing, debugging, and softare engineering that are not being used for this boot camp. --- 09-testing/exercises/test.markdown | 137 ----------------------------- testing/cheat-sheet.md | 50 ----------- testing/outline.md | 7 -- 3 files changed, 194 deletions(-) delete mode 100644 09-testing/exercises/test.markdown delete mode 100644 testing/cheat-sheet.md delete mode 100644 testing/outline.md diff --git a/09-testing/exercises/test.markdown b/09-testing/exercises/test.markdown deleted file mode 100644 index fb25fe1..0000000 --- a/09-testing/exercises/test.markdown +++ /dev/null @@ -1,137 +0,0 @@ -The following exercises do not contain solutions. Yet. Instead, we will be -asking you to submit your solutions to these exercises and then we will post up -solutions at the start of next week. We encourage you to discuss your approaches -or solutions on the course forum! - -To submit your exercises, please create a `testing` folder in your personal -folder in the course repository. Place all of the code and files for theses -exercises in that folder and be sure to check it in. - - -## Exercise 1: Mileage - -The function 'convert_mileage' converts miles per gallon (US style) to liters -per 100 km (metric style): - -```python - gal_to_litre = 3.78541178 - mile_to_km = 1.609344 - - def convert_mileage(mpg): - '''Converts miles per gallon to liters per 100 km''' - litres_per_100_km = 100 / mpg / mile_to_km * gal_to_litre - return litres_per_100_km -``` - -Create a subdirectory in your version control directory called `testing`, then -copy this function into a file in that directory called `mileage.py`. Add more -code to that file to repeatedly ask the user for a mileage in miles per gallon, -and output the mileage in liters per 100 km, until the user enters the string -"`q`". You will need to use the `float()` function to convert from string to a -floating point number. Use the '`if __name__ == "__main__":`' trick to ensure -that the module can be imported without executing your testing code. - -1. Copy `mileage.py` to create `tryexcept.py` Add a try/except block to the new -program to display a helpful message instead of crashing when users enter -invalid input (such as the number "0" or the name of their favorite hockey -team). - -2. Reading the function again, you realize that accepting 0 or negative values -make no sense and should be reported as an error. Look at the exceptions defined -in the `exceptions` module (use the built-in `help(...)` or `dir(...)` -functions) and decide which of Python's built-in exceptions is most appropriate -to use for invalid input. Create a copy of 'tryexcept.py' called 'raiser.py' -that raises this exception; modify the main body of your program to catch it; -and add a comment inside the file explaining why you chose the exception you -did. (Note: you have to call this file `raiser.py`, not `raise.py` because -'import raise' is an error.  Can you see why?) - -3. [According to -Google](http://www.google.ca/search?q=20+miles+per+gallon+in+litres+per+100+km&gbv=1), -20 miles per gallon are equivalent to 11.7607292 liters per 100 km. Use these -values to write a unit test. Keep in mind that these floating values are subject -to truncation and rounding errors. Save the test case in a file called -`test_mileage.py` and run it using the `nosetests` command.  Note: -`test_mileage.py` should use '`from raiser import convert_mileage`' to get the -final version of your mileage conversion function. - -4. Now add a second test case, for 40 miles per gallon equivalent to 5.88036458 -liters per 100 km and run the tests again.  Unless you have already fixed the -error that was present in the initial function, your test should fail.  Find -and fix the error; submit your new function in a file called 'final_mileage.py'. - - -## Exercise 2: Testing Averages - -The results of a set of experiments are stored in a file, where the _i-th_ line -stores the results of the _i-th_ experiment as a comma-separated list of -integers. A student is assigned the task of finding the experiment with the -smallest average value. She writes the following code: - -```python - def avg_line(line): - values = line.split(',') - count = 0 - total = 0 - for value in values: - total += int(value) - count += 1 - return total / count - - def min_avg(file_name): - contents = open(file_name) - averages = [] - for (i, line) in enumerate(contents): - averages.append((avg_line(line), i)) - contents.close() - averages.sort() - min_avg, experiment_number = averages[0] - return experiment_number -``` - -1. Refactor `min_avg` so that it can be tested without depending on external -files. Submit your code in a file called `first_averages.py`. - -2. Write Nose test cases for both functions. Consider what should happen if the -file is empty. Submit your tests in a file called `test_first_averages.py`. -Note: you may assume for now that all input is well formatted, i.e., you do -_not_ have to worry about empty lines, lines containing the names of hockey -teams, etc. - -3. The given specification is ambiguous: what should the result be if two or -more experiments are tied for the minimum average? Copy 'first_averages.py' to -create a new file 'second_averages.py'; modify it to handle this case; add a -comment to the top explaining what rule you decided to use; and create a file -'test_second_averages.py' that tests your changes. - -4. Another student proposed an alternative implementation of the min_avg -function: - -```python - def min_avg(file_name): - contents = open(file_name).readlines() - min_avg = avg_line(contents[0]) - min_index = 0 - for (i,line) in enumerate(contents): - current_avg = avg_line(line) - if current_avg <= min_avg: - min_avg = current_avg - min_index = i - return min_index -``` - -This implementation also finds an experiment with the smallest average, but -possibly a different one than the your function. Modify your test cases so that -both your implementation and this one will pass. (Hint: use the 'in' operator.) - -5. One way to avoid the ambiguity of this specification is to define a -'min_avg_all' function instead, which returns a list with all the experiments -with the smallest average, and let the caller select one. Write tests for the -'min_avg_all' function, considering the following situations: an empty file, -exactly one experiment with minimum average, and more than one experiment with -minimum average. Keep in mind that in the last case, implementations could -return the list in different order. Write the tests the file "test_averages.py". -Use the same data as for the previous tests, if possible. You should use -variables to avoid code duplication. You don't need to implement the -'min_avg_all' function, but your test cases should be comprehensive enough to -serve as a specification for it. diff --git a/testing/cheat-sheet.md b/testing/cheat-sheet.md deleted file mode 100644 index dbc03e0..0000000 --- a/testing/cheat-sheet.md +++ /dev/null @@ -1,50 +0,0 @@ -Testing Cheat Sheet -=================== - -Terminology ------------ - -* A *unit test* acts on an isolated component within an application. -* A *test fixture* is the input data that a test acts on. -* The *interface* of a function is its public face, defined by its - input and output. -* The *implementation* of a function is how it gets from the input to - the output. -* A *stub* is a very simple implementation of one function that is - used in a test of a different function. - -Unit Testing ------------- - -* A *normal case* is a test case that reflects what is expected to be - typical usage of a function. -* A *boundary case* is a test case that reflects a less typical but - potentially troublesome type of usage. - -Exceptions ----------- - -* raise -* catch -* define - -Assertions ----------- - -* syntax -* stops execution - -Unittest --------- - -* extending TestCase -* assertions, e.g. self.assertEquals - -Nose ----- - -* invocation: nosetests -* naming conventions: test_* -* fixtures: setup -* per-test fixtures with @with_setup decorator -* assertions, e.g. assert_equal, assert_almost_equal... diff --git a/testing/outline.md b/testing/outline.md deleted file mode 100644 index 8a60783..0000000 --- a/testing/outline.md +++ /dev/null @@ -1,7 +0,0 @@ -Testing Outline -=============== - -* Testing: how to save time and write better code -* Exceptions: how to handle errors and detect bugs -* Unit tests: how to isolate components of your code and make sure they work -* Floating-point numbers: how to test results that have limited precision -- 2.26.2