Overview
Teaching: 15 min
Exercises: 20 minQuestions
How can I make code more readable?
How can I make code reusable?
Objectives
Write a function taking a fixed number of parameters and having a single point of return.
Write functions whose parameters have default values.
Write functions with multiple points of return.
Write functions that return multiple values.
Extract functions from longer programs.
Trace the execution of nested non-recursive function calls.
Correctly identify the scope of variables.
def
with a name, parameters, and a block of code.def print_greeting():
print('Hello!')
def print_date(year, month, day):
joined = str(year) + '/' + str(month) + '/' + str(day)
print(joined)
print_date(1871, 3, 19)
1871/3/19
return
.return
occurs:
return
produce None
.def average(values):
if len(values) == 0:
return None
return sum(values) / len(values)
a = average([1, 3, 4])
print('average of actual values:', a)
2.6666666666666665
print('average of empty list:', average([]))
None
result = print_date(1871, 3, 19)
print('result of call is:', result)
1871/3/19
result of call is: None
def sum(values, scale=1.0):
result = 0.0
for v in values:
result += v * scale
return result
print('sum with default:', sum([1, 2, 3]))
print('sum with factor:', sum([1, 2, 3], 0.5))
sum with default: 6.0
sum with factor: 3.0
print('out of order:', sum(scale=0.25, values=[1, 2, 3]))
out of order: 1.5
*
.
args
.def total(scale, *args):
result = 0.0
for a in args:
result += a * scale
return result
print('with one value:', total(0.5, 1))
print('with two values:', total(0.5, 1, 3))
with one value: 0.5
with two values: 2.0
red, green, blue = 10, 50, 180
def order(a, b):
if a < b:
return a, b
else:
return b, a
low, high = order(10, 5)
print('order(10, 5):', low, high)
order(10, 5): 5 10
Encapsulation
Fill in the blanks to create a function that takes a single filename as an argument, loads the data in the file named by the argument, and returns the minimum value in that data.
import pandas def min_in_data(____): data = ____ return ____
Find the First
Fill in the blanks to create a function that takes a list of numbers as an argument and returns the first negative value in the list. What does your function do if the list is empty?
def first_negative(values): for v in ____: if ____: return ____
Running Sum
Write a function that calculates the running sum of any number of input arguments, returning the result as a list. For example:
running(1, 2)
=>[1, 3]
running(-5, 2, 7)
=>[-5, -3, 4]
What should
running()
return, and why?
Extracting Functions
People often create functions by extracting pieces of code from scripts they’ve written. Re-write the short program below to have one or more functions so that no single piece of code is more than ten lines long. Do you find the result easier to understand?
# Report the number of lines in each chapter in a text file. # A chapter heading has '##' in the first two columns. # Blank lines are *not* counted in totals. reader = open('thesis.txt', 'r') current_title = None current_count = None for line in reader: line = line.strip() if not line: pass elif line.startswith('##'): if current_title is None: current_title = line current_count = 0 else: print(current_title, current_count) current_title = line current_count = 0 else: current_count = current_count + 1 if current_title is not None: print(current_title, current_count)
Key Points
Use
def
to define a new function.Give parameters default values to make use easier and intent clearer.
Use
*args
to handle variable-length parameter lists.Use
return
at any point to return values.Turn repeated or deeply-nested pieces of code into functions.
Functions temporarily store values on a call stack.