CHAPTER 3

Imperative Programming

3.1 Python Programs

3.2 Execution Control Structures

3.3 User-Defined Functions

3.4 Python Variables and Assignments

3.5 Parameter Passing

3.6 Case Study: Automating Turtle Graphics

Chapter Summary

Solutions to Practice Problems

Exercises

Problems

IN THIS CHAPTER, we discuss how to develop Python programs. A Python program is a sequence of Python statements that are executed in order. To achieve different program behavior depending on a condition, we introduce a few decision and iteration control flow structures that control whether and how many times particular statements are executed.

As we develop more code, we will note that, often, the same group of Python statements is used repeatedly and implements a task that can be described abstractly. Python gives developers the ability to wrap code into functions so the code can be executed with just one function call. One benefit of functions is code reuse. Another is that they simplify the developer's job by (1) hiding the code implementing the function from the developer and (2) making explicit the abstract task achieved by the code. In the chapter case study, we continue the use of turtle graphics to illustrate code reuse, information hiding, and functional abstraction.

The concepts covered in this chapter are fundamental programming language concepts, not just Python concepts. This chapter also introduces the process of breaking down problems into steps that can be described computationally using Python statements.

3.1 Python Programs

In Chapter 2, we used the interactive shell to evaluate Python expressions and execute single Python statements. A Python program that implements a computer application is a sequence of multiple Python statements. This sequence of Python statements is stored in one or more files created by the developer using an editor.

Our First Python Program

In order to write your first program, you will need to use the editor that is included in the Python IDE you are using. How the editor is opened depends on the IDE. For example, if you are using the IDLE Python IDE, click on the image tab in the IDLE window and then on the image button. This will open up a new window, which you will use to type your first Python program.

Module: hello.py
1 line1 = ‘Hello Python developer…’
2 line2 = ‘Welcome to the world of Python!’
3 print(line1)
4 print(line2)

This program consists of four statements, one in each line. Lines 1 and 2 have assignment statements and lines 3 and 4 are calls to the print() function. Once you have typed the program, you will want to execute it. You can do so using your Pyton IDE; again, the steps you need to take to run your program will depend on the type of IDE you are using. For example, if you are using the IDLE IDE, just hit key image on your keyboard (or, using your mouse, click on the image tab of the IDLE shell window menu and the on the image button.) You will be asked to save the program in a file. The file name must have the suffix ‘.py’. After you have saved the file (as hello.py, say, in a folder of your choice), the program is executed and this is printed in the interactive shell:

>>> ========================= RESTART ==========================
>>>
Hello Python developer…
Welcome to the world of Python!

The Python interpreter has executed all the statements in the program in order, from line 1 to line 4. Figure 3.1 shows the flowchart of this program. A flowchart is a diagram that illustrates the flow of execution of a program. In this first example, the flowchart shows that the four statements are executed in order from top to bottom.

image Restarting the Shell

When we executed hello.py, the Python interpreter printed this line before the actual program output:

>>> ======================== RESTART =========================
…

This line indicates that the Python shell got restarted. Restarting the shell has the effect of erasing all the variables that have been defined in the shell so far. The reason why this is necessary is because the program must execute in a blank-slate, default shell environment.

The interactive shell can also be restarted directly. In IDLE, you would do so by clicking on the image tag in the IDLE window and then on the image button. In the next example, we restart the shell after variable x has been assigned 3 and expression x has evaluated to 3:

>>> x = 3
>>> x
3
>>> ======================== RESTART =========================
>>> x
Traceback (most recent call last):
  File “<pyshell#4>”, line 1, in <module>
    x
  NameError: name ‘x’ is not defined
  >>>

In the restarted shell, note that x is no longer defined.

An application program is typically run from outside a software development environments such as IDLE, so it is important to know how to execute Python programs at the command line. An easy way to run your program is to run this command at the prompt of a command line window:

> python hello.py
Hello Python developer…
Welcome to the world of Python!

(Make sure your run the program from within the folder containing the Python program.)

image

Figure 3.1 First program flowchart. Each statement of the program is inside its own box; the program execution flow is shown using arrows connecting the boxes.

image Editors

An editor like Microsoft Word is a poor choice for writing and editing programs. A specialized editor for programmers comes with tools to facilitate and speed up the program development process. Such a software development environment is called an Integrated Development Environment (IDE).

Several IDEs can be used to develop Python programs. Each has features that are helpful for Python programming, including automatic indentation, abilities to run/debug Python code from within the editor, and easy access to the Python Standard Library. Three popular IDEs are IDLE (which is included with the Python development kit), Komodo, and PyDev with Eclipse.

Python Modules

The file hello.py we have created and saved is an example of a user-defined Python module. In Chapter 2, we have used the term module to describe the built-in Standard Library components math, fractions, and turtle. Those are built-in Python modules. What is common between hello.py and the built-in modules we have seen?

A module is simply a file containing Python code. Every file containing Python code and whose file name ends in .py is a Python module. The file hello.py we created is a module, and so are files math.py, fractions.py and turtle.py hidden in some folder on your computer and implementing the corresponding Standard Library components.

The code in a module is, of course, meant to be executed. For example, when we ran hello.py by hitting image, the code in the module got executed, from beginning to end. When we execute an import statement on a module such as math or turtle, it is equivalent to hitting image (well, not quite, but we will handle that in Chapter 7). When we execute

>>> import math

the code in the file math.py gets executed. That Python code just happens to define a bunch of math functions.

Built-In Function print()

Our first program has two lines of code in which the function print() is used. This function prints, within the interactive shell, whatever argument is given to it. For example, if given a number, it prints the number:

>>> print(0)
0

Similarly, if given a list, it prints it:

>>> print([0, 0, 0])
[0, 0, 0]

A string argument is printed without the quotes:

>>> print(‘zero’)
zero

If the input argument contains an expression, the expression is evaluated and the result is printed:

>>> x = 0
>>> print(x)
0

Note that, in our first program, each print() statement “printed” its argument on a separate line.

Interactive Input with input()

Often an executing program needs to interact with the user. The input() function is used for that purpose. It is always used on the right side of an assignment statement, as in:

>>> x = input(‘Enter your first name: ’)

When Python executes this input() function, Python will first print its input argument (string ‘Enter your first name: ’) in the shell:

Enter your first name:

and then it will interrupt the execution and wait for the user to type something at the keyboard. The printed string ‘Enter your first name: ’ is essentially a prompt. When the user types something and hits the image key on her keyboard, the execution will resume and whatever the user has typed will be assigned to variable name:

>>> name = input(‘Enter your first name: ’)
Enter your first name: Ljubomir
>>> name
‘Ljubomir’

Note that Python treats as a string whatever the user types (e.g., Ljubomir in the example).

The input() function is meant to be used in a program. We illustrate this with a more personalized version of the hello.py greeting program. The next program asks the user to enter his first and last name and then prints a personalized greeting on the screen.

Module: input.py
1 first = input(‘Enter your first name: ’)
2 last = input(‘Enter your last name: ’)
3 line1 = ‘Hello ’ + first + ‘ ’ + last + ‘…’
4 print(line1)
5 print(‘Welcome to the world of Python!’)

When we run this program, the statement in line 1 is executed first; it prints the message ‘Enter your first name: ’ and interrupts the execution of the program until the user types something using the keyboard and presses the image key. Whatever the user typed is assigned to variable first. Line 2 is similar. In line 3, string concatenation is used to create the greeting string printed in line 4. Here is a sample execution of the program:

>>>
Enter your first name: Ljubomir
Enter your last name: Perkovic
Hello Ljubomir Perkovic…
Welcome to the world of Python!

image Function input() Returns a String

We just saw that when the input function is called, whatever the user types is treated as a string. Let's check what happens when the user enters a number:

>>> x = input(‘Enter a value for x: ’)
Enter a value for x: 5
>>> x
‘5’

The Python interpreter treats the value entered as a string ‘5’, not integer 5. We check this:

>>> x == 5
False
>>> x == ‘5’
True
The input() function will always treat whatever the user types as a string.

Function eval()

If you expect the user to enter a value that is not a string, you need to explicitly ask Python to evaluate what the user types as a Python expression using the eval() function.

The function eval() takes a string as input and evaluates the string as if it were a Python expression. Here are some examples:

>>> eval(‘3’)
3
>>> eval(‘3 + 4’)
7
>>> eval(‘len([3, 5, 7, 9])’)
4

The function eval() can be used together with the function input() when we expect the user to type an expression (a number, a list, etc.) when requested. All we need to do is wrap the eval() function around the input() function: The effect is that whatever the user types will be evaluated as an expression. For example, here is how we would ensure that a number entered by the user is treated as a number:

>>> x = eval(input(‘Enter x: ’))
Enter x: 5

We check that x is indeed a number and not a string:

>>> x == 5
True
>>> x == ‘5’
False

Practice Problem 3.1

Implement a program that requests the current temperature in degrees Fahrenheit from the user and prints the temperature in degrees Celsius using the formula

image

Your program should execute as follows:

>>>
Enter the temperature in degrees Fahrenheit: 50
The temperature in degrees Celsius is 10.0

3.2 Execution Control Structures

A Python program is a sequence of statements that are executed in succession. In the short programs we have seen so far, the same sequence of statements is executed, in order starting from the statement in line 1 and regardless of the values input by the user, if any. That is not what we usually experience when using an application on a computer. Computer applications usually do different things depending on the values input. For example, the game you just finished playing may stop or continue running, depending on whether you click on the image or the image button. We now introduce Python statements that can control which statements are executed and also which statements should be executed repeatedly.

One-Way Decisions

Suppose we want to develop a program that asks the user to enter the current temperature and then prints an appropriate message only if it is more than 86 degrees. This program would behave as shown if the user enters 87:

>>>
Enter the current temperature: 87
It is hot!
Be sure to drink liquids.

The program would behave as shown if the user enters 67:

>>>
Enter the current temperature: 67

In other words, if the temperature is 86 or less, no message is printed. If the temperature is more than 86, then the message

It is hot!
Be sure to drink liquids.

is printed.

To achieve the described behavior (i.e., the conditional execution of a code fragment) there has to be a way to control whether to execute a fragment of code based on a condition. If the condition is true, then the code fragment is executed; otherwise it is not.

image

Figure 3.2 Flowchart for program oneWay. The input() statement is executed first and the value entered by the user is assigned name temp. The if statement checks condition temp > 86. If true, the two print() statements are executed and the program terminates; if false, the program just terminates.

The if statement is used to implement conditional execution. Here is how we would use the if statement to implement the desired program:

Module: oneWay.py
1 temp = eval(input(‘Enter the current temperature: ’))
2
3 if temp > 86:
4     print(‘It is hot!’)
5     print(‘Be sure to drink liquids.’)

(Note the use of a blank line to make the program more readable.) The if statement encompasses line 3 through 5 in the program. In line 3, the if keyword is followed by the condition temp > 86. If the condition evaluates to True, the indented statements below line 3 are executed. If the condition temp > 86 evaluates to False, those indented statements are not executed. Figure 3.2 illustrates (using dashed lines) the two possible execution flows for the program.

Now suppose that we need to add a feature to our program: We would like the program to print ‘Goodbye!’ before terminating, whether the temperature input by the user is high or not. The program would need to behave as follows:

>>>
Enter the current temperature: 87
It is hot!
Be sure to drink liquids.
Goodbye.

or as follows

>>>
Enter the current temperature: 67
Goodbye.

image

Figure 3.3 Flowchart for program oneWay2. Regardless of whether the if statement condition is true or false, the statement print(‘Goodbye.’) is executed after the if statement.

A print(‘Goodbye’) needs to be executed after the if statement. This means that the print(‘Goodbye’) statement must be placed in the program (1) below the indented if block of code and (2) with the same indentation as the first line of the if statement:

Module: oneWay2.py
1 temp = eval(input(‘Enter the current temperature: ’))
2
3 if temp > 86:
4     print(‘It is hot!’)
5     print(‘Be sure to drink liquids.’)
6
7 print(‘Goodbye.’)

After line 3 of this program is executed, either the indented block of code in lines 4 and 5 is executed, or it is not. Either way, the execution resumes with the statement in line 7. The flowchart corresponding to program oneWay2.py is shown in Figure 3.3.

In general, the format of an if statement is:

if <condition>:
    <indented code block>
<non-indented statement>

The first line of an if statement consists of the if keyword, followed by Boolean expression <condition> (i.e., an expression that evaluates to True or False), followed by a colon, which indicates the end of the condition. Below the first line and indented with respect to the if keyword will be the block of code that is executed if condition evaluates to True.

If <condition> evaluates to False, the indented block of code is skipped. In either case, whether the indented code has been executed or not, the execution continues with the Python statement <non-indented statement> directly below, and with the same indentation as, the first line of the if statement.

image Indentation

In Python, proper indentation of Python statements is critical. Compare

if temp > 86:

    print(‘Its hot!’)
    print(‘Be sure to drink liquids.’)

print(‘Goodbye.’)

with

if temp > 86:

   print(‘It is hot!’)
   print(‘Be sure to drink liquids.’)
   print(‘Goodbye.’)

In the first code fragment, the statement print(‘Goodbye.’) has the same indentation as the first line of the if statement. It is therefore a statement that is executed after the if statement, regardless of whether the if statement condition is true or false.

In the second code fragment, the statement print(‘Goodbye.’) is indented with respect to the first line of the if statement. It is therefore part of the block that is executed only if the if statement condition is true.

Practice Problem 3.2

Translate these conditional statements into Python if statements:

  1. If age is greater 62, print ‘You can get your pension benefits’.
  2. If name is in list [‘Musial’, ‘Aaraon’, ‘Williams’, ‘Gehrig’, ‘Ruth’], print ‘One of the top 5 baseball players, ever!’.
  3. If hits is greater than 10 and shield is 0, print ‘You are dead…’.
  4. If at least one of the Boolean variables north, south, east, and west is True, print ‘I can escape.’.

Two-Way Decisions

In a one-way decision if statement, an action is performed only if a condition is true. Then, whether the condition is true or false, execution resumes with the statement following the if statement. In other words, no special action is performed if the condition is false.

Sometimes, however, that is not what we want. We may need to perform one action when the condition is true and another if the condition is false. Continuing with the temperature example, suppose we would like to print an alternative message if the value of temp is not greater than 86. We can achieve this behavior with a new version of the if statement, one that uses the else clause. We use program twoWay.py to illustrate this.

Module: twoWay.py
 1 temp = eval(input(‘Enter the current temperature: ’))
 2
 3 if temp > 86:
 4
 5     print(‘It is hot!’)
 6     print(‘Be sure to drink liquids.’)
 7
 8 else:
 9
10     print(‘It  is not hot.’)
11     print(‘Bring a jacket.’)
12
13 print(‘Goodbye.’)

When line 3 of the program is executed, there are two cases. If the value of temp is greater than 86, the indented block

print(‘It is hot!’)
print(‘Be sure to drink liquids.’)

is executed. If temp is not greater than 86, the indented block below else is executed instead:

print(‘It is not hot.’)
print(‘Bring a jacket.’)

In both cases, execution resumes with the statement following, and indented the same as, the if/else statement (i.e., the statement in line 13). The flowchart illustrating the two possible execution flows is shown in Figure 3.4.

image

Figure 3.4 Flowchart for program twoWay. If the condition temp > 86 is true, the body of the if statement gets executed; if false, the body of the else clause gets executed. In both cases, execution resumes with the statements after the if/else pair of statements.

The more general version of the if statement has the following format:

if <condition>:
    <indented code block 1>
else:
    <indented code block 2>
<non-indented statement>

The indented code section <indented code block 1> is executed if <condition> evaluates to True; if <condition> evaluates to False, the indented code section <indented code block 2> is executed instead. After executing one or the other code block, execution resumes with the statement <non-indented statement>.

Practice Problem 3.3

Translate these into Python if/else statements:

  1. If year is divisible by 4, print ‘Could be a leap year.’; otherwise print ‘Definitely not a leap year.’
  2. If list ticket is equal to list lottery, print ‘You won!’; else print ‘Better luck next time…’

Practice Problem 3.4

Implement a program that starts by asking the user to enter a login id (i.e., a string). The program then checks whether the id entered by the user is in the list [‘joe’, ‘sue’, ‘hani’, ‘sophie’] of valid users. Depending on the outcome, an appropriate message should be printed. Regardless of the outcome, your function should print ‘Done.’ before terminating. Here is an example of a successful login:

>>>
Login: joe
You are in!
Done.

And here is one that is not:

>>>
Login: john
User unknown.
Done.

Iteration Structures

In Chapter 2 we introduced strings and lists. Both are sequences of objects. A string can be viewed as a sequence of one-character strings; a list is a sequence of objects of any type (strings, numbers, even other lists). A task that is common to all sequences is to perform an action on every object in the sequence. For example, you could go down your list of contacts and send a party invite to contacts living nearby. Or you could go through a shopping list to check that you purchased everything on it. Or you could go through the characters of your name in order to spell it.

Let's use this last example. Suppose we would like to implement a short program that spells the string entered by the user:

>>>
Enter a word: Lena
The word spelled out:
L
e
n
a

The program first requests the user to enter a string. Then, after printing the line ‘The word spelled out:’, the characters of the string entered by the user are printed one per line. We can start the implementation of this program as follows:

name = input(‘Enter a word: ’)
print(‘The word spelled out:’)
…

In order to complete this program, we need a method that will allow us to execute a print() statement for every character of the string name. The Python for loop statement can be used to do exactly this. This program implements the behavior we want:

Module: spelling.py
1 name = input(‘Enter a word: ’)
2 print(‘The word spelled out: ’)
3
4 for char in name:
5     print(char)

The for loop statement encompasses lines 4 and 5 of the program. In line 4, char is a variable name. The for loop statement will repeatedly assign characters of string name to variable char. If name is string ‘Lena’, char will first have value ‘L’, then ‘e’, then ‘n’, and finally ‘a’. For each value of char, the indented print statement print(char) is executed. Figure 3.5 illustrates the workings of this loop.

image

Figure 3.5 Iteration through a string. The variable char is assigned ‘L’ in iteration 1, ‘e’ in iteration 2, ‘n’ in iteration 3, and ‘a’ in iteration 4; in every iteration, the current value of char is printed. So when char is ‘L’, ‘L’ gets printed; when char is ‘e’, ‘e’ gets printed, and so on.

The for loop can also be used to iterate over the items of a list. In the next example, we use, in the interactive shell, a for loop to iterate over string objects representing my pets:

>>> animals = [‘fish’, ‘cat’, ‘dog’]
>>> for animal in animals:
        print(animal)

fish
cat
dog

The for loop executes the indented section print(animal) three times, once for each value of animal; the value of animal is first ‘fish’, then ‘cat’, and finally ‘dog’, as illustrated in Figure 3.6.

image

Figure 3.6 Iteration through a list. The value of variable animal is set to ‘fish’ in iteration 1, then to ‘cat’ in iteration 2, and finally to ‘dog’. In each iteration, the value of animal is printed.

image The for Loop Variable

The variable char in

for char in name:
    print(char)

and the variable animal in

for animal in animals:
    print(animal)

are just variable names, chosen to make the program more meaningful. We could have just as easily written the loops with, say, variable name x:

for x in name:
    print(x)

for x in animals:
    print(x)

Note: If we change the name of the for loop variable, we also need to change any occurrence of it in the body of the for loop.

In general, the for loop statement has this format:

for <variable> in <sequence>:
    <indented code block >
<non-indented code block>

The for loop will successively assign objects from <sequence> to <variable>, in order as they appear from left to right. The <indented code block>, typically called the body of the for loop, is executed once for every value of <variable>. We say that the for loop iterates through the objects in the sequence. After <indented code block> has been executed for the last time, execution resumes with the statements after the for loop; they will be below, and use the same indentation as, the first line of the for loop statement.

Nesting Control Flow Structures

Let's use the for loop to write a program that combines a for loop and an if statement. We would like to write an application that starts by asking the user to enter a phrase. After the user has done so, the program will print all the vowels in the phrase, and no other letter. The program should behave like this:

>>>
Enter a phrase: test case
e
a
e

This program will consist of several components. We need an input() statement to read in the phrase, a for loop to iterate over the characters of the input string, and, in every iteration of the for loop, an if statement to check whether the current character is a vowel. If so, it gets printed. Next is the complete program.

Module: for.py
1 phrase = input(‘Enter a phrase: ’)
2
3 for c in phrase:
4     if c in ‘aeoiuAEIOU’:
5         print(c)

Note that we combined a for loop and an if statement and that indentation is used to specify the body of each. The if statement body is just print(c) while the for loop statement body is:

if c in ‘aeiouAEIOU’:
    print(c)

Practice Problem 3.5

Implement a program that requests from the user a list of words (i.e., strings) and then prints on the screen, one per line, all four-letter strings in the list.

>>>
Enter word list: [‘stop’, ‘desktop’, ‘top’, ‘post’])
stop
post

Function range()

We just saw how the for loop is used to iterate over the items of a list or the characters of a string. It is often necessary to iterate over a sequence of numbers in a given range, even if the list of numbers is not explicitly given. For example, we may be searching for a divisor of a number. Or we could be iterating over the indexes 0, 1, 2,… of a sequence object. The built-in function range() can be used together with the for loop to iterate over a sequence of numbers in a given range. Here is how we can iterate over the integers 0, 1, 2, 3, 4:

>>> for i in range(5):
        print(i)

0
1
2
3
4

Function range(n) is typically used to iterate over the integer sequence 0, 1, 2,…, n 1. In the last example, variable i is set to 0 in the first iteration; in the following iterations, i gets assigned values 1, 2, 3, and finally 4 (as n = 5). As in previous for loop examples, the indented code section of the for loop is executed in every iteration, for every value of i.

Practice Problem 3.6

Write the for loop that will print these sequences of numbers, one per line, in the interactive shell.

  1. Integers from 0 to 9 (i.e., 0, 1, 2, 3, 4, 5, 6, 7, 8, 9)
  2. Integers from 0 to 1 (i.e., 0, 1)

The range() function can also be used to iterate over more complex sequences of numbers. If we would like the sequence to start at a nonzero number start and end before number end, we make the function call range(start, end). For example, this for loop iterates over the sequence 2, 3, 4:

>>> for i in range(2, 5):
        print(i)

2
3
4

In order to generate sequences that use a step size other than 1, a third argument can be used. The function call range(start, end, step) can be used to iterate over the sequence of integers starting at start, using a step size of step and ending before end. For example, the next loop will iterate over the sequence 1, 4, 7, 10, 13:

>>> for i in range(1, 14, 3):
        print(i)

The sequence printed by the for loop starts at 1, uses a step size of 3, and ends before 14. Therefore it will print 1, 4, 7, 10, and 13.

Practice Problem 3.7

Write the for loop that will print the following sequences of numbers, one per line.

  1. Integers from 3 up to and including 12
  2. Integers from 0 up to but not including 9, but with a step of 2 instead of the default of 1 (i.e., 0, 2, 4, 6, 8)
  3. Integers from 0 up to but not including 24 with a step of 3
  4. Integers from 3 up to but not including 12 with a step of 5

3.3 User-Defined Functions

We have already seen and used several built-in Python functions. The function len(), for example, takes a sequence (a string or a list, say) and returns the number of items in the sequence:

>>> len(‘goldfish’)
8
>>> len([‘goldfish’, ‘cat’, ‘dog’])
3

Function max() can take two numbers as input and returns the maximum of the two:

>>> max(4, 7)
7

Function sum() can take a list of numbers as input and returns the sum of the numbers:

>>> sum([4, 5, 6, 7])
22

Some functions can even be called without arguments:

>>> print()

In general, a function takes 0 or more input arguments and returns a result. One of the useful things about functions is that they can be called, using a single-line statement, to complete a task that really requires multiple Python statements. Even better, usually the developer using the function does not need to know what those statements are. Because developers do not need to worry about how functions work, functions simplify the development of programs. For this reason, Python and other programming languages make it possible for developers to define their own functions.

Our First Function

We illustrate how functions are defined in Python using the next example: a Python function that takes a number as input and computes and returns the value x2 + 1. We expect this function to behave like this:

>>> f(9)
82
>>> 3 * f(3) + 4
34

Function f() can be defined in a Python module as:

Module: ch3.py
1  def f(x):
2    return x**2 + 1

In order to use function f() (to compute, say, f(3) or f(9)), we first have to execute this two-line statement by running the module containing it (e.g., by pressing image). After the function definition statement has been executed, function f() can be used.

You can also define function f() directly in the interactive shell in this way:

>>> def f(x):
        return x**2 + 1

Let's check whether it is defined:

>>> 2 * f(2)
10

The Python function definition statement has this general format:

def <function name> (<0 or more variables>):
    <indented function body>

A function definition statement starts with the def keyword. Following it is the name of the function; in our example, the name is f. Following the name and in parentheses are the variable names that stand in for the input arguments, if any. In function f(), the x in

def f(x):

has the same role as x in the math function f (x): to serve as the name for the input value.

The first line of the function definition ends with a colon. Below and indented is the body of the function, a set of Python statements that implement the function. They are executed whenever the function is called. If a function is to return a value, then the return statement is used to specify the value to be returned. In our case, the value x2 + 1 is returned.

Practice Problem 3.8

Define, directly in the interactive shell, function average() that takes two numbers as input and returns the average of the numbers. A sample usage is:

>>> average(2, 3.5)
2.75

Practice Problem 3.9

Implement function perimeter() that takes, as input, the radius of a circle (a nonnegative number) and returns the perimeter of the circle. You should write your implementation in a module you will name perimeter.py. A sample usage is:

>>> perimeter(1)
6.283185307179586

Not all functions need to return a value, as we will see in the next example.

print() versus return

As another example of a user-defined function, we develop a personalized hello() function. It takes as input a name (a string) and prints a greeting:

>>> hello(‘Sue’)
Hello, Sue!

We implement this function in the same module as function f():

<b>Module:</b> ch3.py
1 def hello(name):
2     print(‘Hello, ’+ name + ‘!’)

When function hello() is called, it will print the concatenation of string ‘Hello, ’, the input string, and string ‘!’.

Note that function hello() prints output on the screen; it does not return anything. What is the difference between a function calling print() or returning a value?

Statement return versus Function print() image

A common mistake is to use the print() function instead of the return statement inside a function. Suppose we had defined function f() in this way:

def f(x):
  print(x**2 + 1)

It would seem that such an implementation of function f() works fine:

>>> f(2
5

However, when used in an expression, function f() will not work as expected:

>>> 3 * f(2) + 1
5
Traceback (most recent call last):
  File ‘<pyshell#103>’, line 1, in <module>
    3 * f(2) + 1
TypeError: unsupported operand type(s) for *:
           ‘int’ and ‘NoneType’

When evaluating f(2) in the expression 3 * f(2) + 1, the Python interpreter evaluates (i.e., executes) f(2), which prints the value 5. You can actually see this 5 in the line before the “Traceback” error line.

So f() prints the computed value, but it does not return it. This means that f(2) returns nothing and thus evaluates to nothing in an expression. Actually, Python has a name for the “nothing” type: It is the ‘NoneType’ referred to in the error message shown. The error itself is caused by the attempt to multiply an integer value with “nothing.”

That said, it is perfectly OK to call print() inside a function, as long as the intent is to print rather than return a value.

Practice Problem 3.10

Write function negatives() that takes a list as input and prints, one per line, the negative values in the list. The function should not return anything.

>>> negatives([4, 0, -1, -3, 6, -9])
-1
-3
-9

Function Definitions Are “Assignment” Statements

To illustrate that functions are really ordinary Python statements, similar in fact to assignment statements, we use this short program:

Module: dynamic.py
1 s = input(‘Enter square or cube: ’)
2 if s == ‘square’:
3     def f(x):
4         return x*x
5 else:
6     def f(x):
7         return x*x*x

In it, function f() is defined within a Python program, just as an assignment statement can be in a program. The actual definition of f() depends on the input entered by the user at execution time. By typing cube at the prompt, function f() is defined to be the cubic function:

>>>
Enter square or cube: cube
>>> f(3)
27

If, however, the user types square, then f() would be the quadratic function.

image First Define the Function, Then Use It

Python does not allow calling a function before it is defined, just as a variable cannot be used in an expression before it is assigned.

Knowing this, try to figure out why running this module would result in an error:

print(f(3))

def f(x):
    return x**2 + 1

Answer: When a module is executed, the Python statements are executed top to bottom. The print(f(3)) statement will fail because the name f is not defined yet.

Will we get an error when running this module?

def g(x):
    return f(x)

def f(x):
    return x**2 + 1

Answer: No, because functions f() and g() are not executed when the module is run, they are just defined. After they are defined, they can both be executed without problems.

Comments

Python programs should be well documented for two reasons:

  1. The user of the program should understand what the program does.
  2. The developer who develops and/or maintains the code should understand how the program works.

Documentation for the program developer and the future maintainer is important because undocumented code is harder to maintain, even by the programmer who wrote the code. Such documentation is done mainly using comments written by the function developer right next the program.

A comment is anything that follows the # symbol in a line. Here is how we add a comment to explain the implementation of function f():

Module: ch3.py
1 def f(x):
2   return x**2 + 1   # f(x) should evaluate to x*x + 1

The comment—anything that follows # in the line—is ignored by Python.

While comments are necessary, it is also important not to overcomment. Comments should not make it difficult to read the program. Ideally, your programs should use meaningful variable names and simple, well-designed code so the program is, or is almost, self-explanatory. That is actually easier to achieve in Python than in most other languages. Comments should be used to identify the main components of the program and explain the trickier parts.

Docstrings

Functions should also be documented for the function users. The built-in functions we have seen so far all have documentation that can be viewed using function help(). For example:

>>> help(len)
Help on built-in function len in module builtins:

len(…)
    len(object) -> integer

    Return the number of items of a sequence or mapping.

If we use help on our first function f(), surprisingly we get some documentation as well.

>>> help(f)
Help on function f in module _ _main_ _:

f(x)

In order to get something more useful, however, the function developer needs to add a special comment to the function definition, one that will be picked up by the help() tool. This comment, called a docstring, is a string that should describe what the function does and must be placed directly below the first line of a function definition. Here is how we would add docstring ‘returns x**2+1’ to our function f():

Module: ch3.py
1  def f(x):
2      ‘returns x**2 + 1’
3      return x**2 + 1    # compute x**2 + 1 and return obtained value

Let's also add a docstring to our function hello():

Module: ch3.py
1  def hello(name):
2      ‘a personalized hello function’
3      print(‘Hello,’ + name + ‘ !’)

With the docstrings in place, the help() function will use them as part of the function documentation. For example, the docstring ‘returns x**2+1’ is displayed when viewing the documentation for function f():

>>> help(f)
Help on function f in module _ _main_ _:

f(x)
     returns x**2 + 1

Similarly, the docstring is displayed when viewing the documentation for hello():

>>> help(hello)
Help on function hello in module _ _main_ _:

hello(name)
    a personalized hello function

Practice Problem 3.11

Add docstring returns average of x and y to function average() and docstring prints the negative numbers in list lst to function negatives() from Practice Problems 3.8 and 3.10. Check your work using the help() documentation tool. You should get, for example:

>>> help(average)
Help on function average in module _ _main_ _:

average(x, y)
    returns average of x and y

3.4 Python Variables and Assignments

Functions are either called from within the interactive shell or by another program, which we will refer to as the calling program. In order to be able to design functions, we need to understand how values created in the calling program—or the interactive shell—are passed as input arguments to the function. To do this, however, we first need to understand exactly what happens in an assignment statement.

Let's consider this question in the context of the assignment a = 3. First, let's note that before executing this assignment, the identifier a does not exists:

>>> a
Traceback (most recent call last):
  File “<pyshell#15>”, line 1, in <module>
    a
NameError: name ‘a’ is not defined

When the assignment

>>> a = 3

is executed, the integer object 3 and its name a are created. Python will store the name in a table maintained by Python. This is illustrated in Figure 3.7.

image

Figure 3.7 Assignments to new variables. The int object (with value) 3 is assigned to variable a, the float object 3.0 is assigned to b, the str object ‘hello’ is assigned to c, and the list object [2, 3, 5, 8, 11] is assigned to d.

The variable a now refers to the integer object with value 3:

>>> a
3

Figure 3.7 shows that additional variables are in the table: variable b referring to float object 3.0, variable c referring to str object ‘hello’, and variable d referring to list object [2, 3, 5, 8, 11]. In other words, it illustrates that these assignments have also been made:

>>> b = 3.0
>>> c = ‘hello’
>>> d = [2, 3, 5, 8, 11]

In general, a Python assignment statement has this syntax:

<variable> = <expression>

The <expression> to the right of the = assignment operator is evaluated and the resulting value is stored in an object of the appropriate type; then the object is assigned to <variable>, which is said to refer to the object or to be bound to the object.

Mutable and Immutable Types

Subsequent assignments to a, such as

>>> a = 6

will reuse the existing name a. The result of this assignment is that variable a will be refer to another object, integer object 6. The int object 3 no longer is referred to by a variable, as shown in Figure 3.8.

image

Figure 3.8 Assigning an immutable object to an existing variable. The int object 6 is assigned to existing variable a; the int object 3 is no longer assigned to a variable and can no longer be accessed.

The important thing to note is that the assignment a = 6 did not change the value of the integer object 3. Instead, a new integer object 6 is created, and variable a now refers to it. In fact, there is no way to change the value of the object containing value 3. This illustrates an important feature of Python: Python int objects cannot be changed. Integer objects are not the only objects that cannot be modified. Types whose objects cannot be modified are called immutable. All Python number types (bool, int, float, and complex) are immutable.

We saw in Chapter 2 that a list object can change. For example:

>>> d = [2, 3, 5, 8, 11]
>>> d[3] = 7
>>> d
[2, 3, 5, 7, 11]

The list d is modified in the second statement: the entry at index 3 is changed to 7, as shown in Figure 3.9. Types whose objects can be modified are called mutable types. The list type is mutable. The number types are immutable. What about the string type?

image

Figure 3.9 Lists are mutable. The assignment d[3] = 7 replaces the object at index 3 of d with new int object 7.

>>> c =  ‘hello’
>>> c[1] =  ‘i’
Traceback (most recent call last):
  File “<pyshell#23>”, line 1, in <module>
    c[1] =  ‘i’
TypeError: ‘str’ object does not support item assignment

We cannot modify a character of string object. The string type is immutable.

Assignments and Mutability

We often have the situation when multiple variables refer to the same object. (This is, in particular, the case when a value is passed as an input to a function.) We need to understand what happens when one of the variables is assigned another object. For example, suppose we do:

>>> a = 3
>>> b = a

The first assignments creates an integer object with value 3 and gives it name a. In the second assignment, the expression a evaluates to the integer object 3, which then receives another name, b, as shown in Figure 3.10:

image

Figure 3.10 Multiple references to the same object. The assignment b = a evaluates the expression to the right of the = sign to object 3 and assigns that object to variable b.

Now, what happens when we assign something else to a?

>>> a = 6

The assignment a = 6 does not change the value of the object from 3 to 6 because the int type is immutable. Variable a should now refer to a new object with value 6. What about b?

>>> a
6
>>> b
3

Variable b still refers to the object with value 3, as shown in Figure 3.11:

image

Figure 3.11 Multiple assignments and mutability. If a and b refer to the same object 3 and then object 6 is assigned to a, b will still refer to object 3.

The point is this: If two variables refer to the same immutable object, that modifying one variable will not affect the other.

Now let's consider what happens with lists. We start by assigning a list to a and then assigning a to b.

>>> a = [3, 4, 5]
>>> b = a

We expect a and b to refer to the same list. That is indeed the case, as shown in Figure 3.12:

image

Figure 3.12 Multiple assignments on a mutable object. Both a and b refer to the same list; the assignment b[1] = 8 and the assignment a[-1] = 16 will change the same list, so any change to the list referred by b will change the list referred to by a and vice versa.

Now let's see what happens when we assign a new object to b[1]:

>>> b[1] = 8
>>> b
[3, 8, 5]
>>> a
[3, 8, 5]

As we saw in Chapter 2, lists can be modified. The list b is modified by the assignment b[1] = 8. But because variable a is bound to the same list, a will be changed as well. Similarly, changes to list a will modify list b: assignment a[-1] = 16 will make new object 16 be the last object in lists a and b.

Practice Problem 3.12

Draw a diagram representing the state of names and objects after this execution:

>>> a = [5, 6, 7]
>>> b = a
>>> a = 3

Swapping

We now consider a fundamental assignment problem. Let a and b refer to two integer values:

>>> a = 6
>>> b = 3

Suppose we need to swap the values of a and b. In other words, after the swap, a will refer to 3 and b will refer to 6, as shown in Figure 3.13.

image

Figure 3.13 Swapping values. Variables a and b swap the objects they refer to; Python supports the multiple assignment statement, which makes swapping easy.

If we start by assigning the value of b to a:

a = b

then variable a will refer to the same object that variable b refers to. So we will have both a and b refer to 3 and we would have “lost” integer object 6. Before we execute a = b, we must save a reference to 6 and then assign that to b at the end:

>>> temp = a   # temp refers to 6
>>> a = b      # a refers to 3
>>> b = temp   # b refers to 6

In Python, there is a much simpler way to achieve the swap. Python supports the multiple assignment statement:

>>> a = 6
>>> b = 3
>>> a, b = b, a
>>> a
3
>>> b
6

In the multiple assignment statement a, b = b, a, the two expressions on the right of = are evaluated to two objects and then each is assigned to the corresponding variable.

Before we move on from our discussion of Python assignments, we note another cool Python feature. A value can be assigned to several variables simultaneously:

>>> i = j = k = 0

The three variables i, j, and k are all set to 0.

Practice Problem 3.13

Suppose a nonempty list team has been assigned. Write a Python statement or statements that swap the first and last value of the list. So, if the original list is:

>>> team = [‘Ava’, ‘Eleanor’, ‘Clare’, ‘Sarah‘]

then the resulting list should be:

>>> team
[‘Sarah‘, ‘Eleanor’, ‘Clare’, ‘Ava’]

3.5 Parameter Passing

With a better understanding of how assignments happen in Python, we can understand how input arguments are passed in function calls. Functions are either called from within the interactive shell or by another program. We refer to either as the calling program. The input arguments in a function call are names of objects created in the calling program. These names may refer to objects that are mutable or immutable. We separately consider each case.

Immutable Parameter Passing

We use the function g() to discuss the effect of a passing a reference to an immutable object in a function call.

Module: ch3.py
1  def g(x):
2      x = 5

Let's start by assigning integer 3 to variable name a:

>>> a = 3

In this assignment statement, integer object 3 is created and given name a, as shown in Figure 3.14:

image

Figure 3.14 An assignment in the main program. Integer object 3 is assigned name a in the main program, the interactive shell.

This figure illustrates that name a has been defined in the context of the interactive shell. It refers to an integer object whose value is 3. Now let's call function g() with name a as the input argument:

>>> g(a)

When this function call is made, the argument a is evaluated first. It evaluates to integer object 3. Now, recall that function g() was defined as:

def g(x):
    x = 5

The name x in def g(x): is now set to refer to the input integer object 3. In effect, it is as if we have executed the assignment x = a:

image

Figure 3.15 Parameter passing. The function call g(a) passes the reference a as the input argument. Variable x, defined at the beginning of the execution of g(), will be assigned this reference. Both a and x will refer to the same object.

Thus, at the start of the execution of g(a), there are two variables that refer to the single object 3: variable a defined in the interactive shell and variable x defined in function g() (see Figure 3.15).

During the execution of g(a), variable x is assigned 5. Since integer objects are immutable, a no longer refers to 3 but to new integer object 5, as shown in Figure 3.16. Variable a, however, still refers to object 3.

image

Figure 3.16 Immutable parameter passing. When x = 5 is executed, x will refer to a new integer object with value 5. The integer object with value 3 is unchanged. The name a in the main program, the interactive shell, still refers to it.

The point of this example is this. The function g() did not, and cannot, modify the value of a in the interactive shell. In general, when calling and executing a function, the function will not modify the value of any variable passed as a function argument if the variable refers to an immutable object.

What if we pass a reference to a mutable object, however?

Mutable Parameter Passing

We use the next function to see what happens when the name of a mutable object is passed as the argument of a function call.

Module: ch3.py
1  def h(lst):
2      lst[0] = 5

Consider what happens when we execute:

>>> myList = [3, 6, 9, 12]
>>> h(myList)

In the assignment statement, a list object is created and assigned name myList. Then the function call h(myList) is made. When function h() starts executing, the list referred to by myList will be assigned to variable name lst defined in the function definition of h(). So we have the situation illustrated in Figure 3.17.

image

Figure 3.17 Mutable parameter passing. The function call h() passes the reference to a list as an argument. So name myList in the interactive shell and name lst in h() now refer to the same list.

While executing function h(), lst[0] is assigned 5 and so lst[0] will refer to new object 5. Since lists are mutable, the list object referred to by lst changes. Because variable myList in the interactive shell refers to the same list object, it means that the list object referred to by myList changes as well. We illustrate this in Figure 3.18.

image

Figure 3.18 Functions can modify mutable arguments. Since lists are mutable, the assignment lst[0] = 5 replaces the list entry at index 0 to 5. Since name myList in the main program, the interactive shell, refers to the same list, the change will be visible in the main program.

This example illustrates that when a mutable object, like list object [3,6,9,12], is passed as an argument in a function call, it may be modified by the function.

Practice Problem 3.14

Implement function swapFL() that takes a list as input and swaps the first and last elements of the list. You may assume the list will be nonempty. The function should not return anything.

>>> ingredients = [‘flour’, ‘sugar’, ‘butter’, ‘apples’]
>>> swapFL(ingredients)
>>> ingredients
[‘apples’, ‘sugar’, ‘butter’, ‘flour’]

3.6 Case Study: Automating Turtle Graphics

In Chapter 2 we implemented a sequence of Python statements—in other words, a program—that draws the picture of a smiley face. Take a another look at this sequence of statements. You will notice that the statements were repetitive and somewhat tedious to type. This sequence of commands appeared several times:

t.penup()
t.goto(x, y)
t.pendown()

This sequence of Turtle method calls was used to move the Turtle object t to a new location (with coordinates (x, y)) without leaving a trace; in other words, it was used to make the Turtle object jump to the new location.

It would save us a lot of typing if we could replace that sequence of Python statements with just one. That is exactly what functions are for. What we want to do is to develop a function that takes a Turtle object and coordinates x and y as input arguments and makes the Turtle object jump to coordinate (x, y). Here is that function:

Module: turtlefunctions.py
1  def jump(t, x, y):
2      ‘makes turtle t jump to coordinates (x, y)’
3
4      t.penup()
5      t.goto(x, y)
6      t.pendown()

Using this function instead of three statements shortens the process of drawing the smiley face image. It also makes the program more understandable because the function call jump(t, x, y):

  1. Better describes the action performed by the Turtle object
  2. Hides the low-level and technical pen-up and -down operations, thus removing complexity from the program.

Suppose now we want to be able to draw several smiley faces next to each other as shown in Figure 3.19.

image

Figure 3.19 Two smiley faces. Ideally, each smiley face should be drawn with just one function call.

To do this, it would be useful to develop a function that takes as input a Turtle object and coordinates x and y and draws a smiley face at coordinate (x, y). If we name this function emoticon(), we could use and reuse it to draw the image.

>>> import turtle
>>> s = turtle.Screen()
>>> t = turtle.Turtle()
>>> emoticon(t, -100, 100)
>>> emoticon(t, 150, 100)

Here is the implementation of the function:

Module: ch3.py
 1  def emoticon(t,x,y):
 2      ‘turtle t draws a smiley face with chin at coordinate (x, y)’
 3      # set turtle direction and pen size
 4      t.pensize(3)
 5      t.setheading(0)
 6
 7      # move to (x, y) and draw head
 8      jump(t, x, y)
 9      t.circle(100)
10
11      # draw right eye
12      jump(t, x+35, y+120)
13      t.dot(25)
14
15      # draw left eye
16      jump(t, x-35, y+120)
17      t.dot(25)
18
19      #draw smile
20      jump(t, x-60.62, y+65)
21      t.setheading(-60) # smile is a 120 degree
22      t.circle(70, 120) # section of a circle

We should note a few things about the program. Note the docstring with the strange triple quotes. In Python, strings, statements, and most expressions usually cannot span multiple lines. A string, whether defined with single quotes, as in ‘example’, or with double quotes, as in “example”, cannot span multiple lines of a Python program. If, however, we need to define a string that does contain multiple lines, we must use triple quotes, as in ‘‘‘example’’’ or “““example”””.

The rest of the function follows the steps we have already developed in the case study in Chapter 2. Note how we use the jump() function to make the program shorter and the steps of the program more intuitive.

Practice Problem 3.15

Implement function olympic(t) that makes turtle t draw the Olympic rings shown below. Use the jump() function from module ch3. You should be able to get the image drawn by executing:

>>> import turtle
>>> s = turtle.Screen()
>>> t = turtle.Turtle()
>>> olympic(t)

image

Chapter Summary

Chapter 3 introduces tools for writing Python programs and basic program development concepts.

We start by writing very simple interactive programs that use built-in functions print(), input(), and eval(). Then, to create programs that execute differently depending on the input entered by the user, we introduce the if statement. We describe its one-way and two-way decision formats.

We introduce next the for loop statement, in its simplest form: as a way to iterate over the items of a list or the characters of a string. We also introduce the range() function, which enables iteration over a sequence of integers in a given range.

A focus of this chapter is how to define new functions in Python. The syntax of a function definition statement is introduced. We pay special attention to parameter passing (i.e., how parameters are passed when calling a function). To understand parameter passing, we take a closer look at how assignments work. Finally, we introduce the ways to document a function, through comments and a docstring.

In the case study, we showcase the benefits of functions—code reuse and hiding the implementation details—by developing several turtle graphics functions.

Solutions to Practice Problems

3.1 An input() statement is used to request a temperature. The value entered by the user is treated as a string. One way to convert the string value to a number is with the eval() function, which evaluates the string as an expression. An arithmetic expression is used for the conversion from degrees Fahrenheit to degrees Celsius and the result is then printed.

fahr = eval(input(‘Enter the temperature in degrees Fahrenheit: ’))
cels = (fahr - 32) * 5 / 9
print(‘The temperature in degrees Celsius is’, cels)

3.2 The if statement in the interactive shell is shown without the result of the execution:

>>> if age > 62:
        print(‘You can get your pension   benefits!’)
>>> if name in [‘Musial’,‘Aaron’,‘Williams’,‘Gehrig’,‘Ruth’]:
        print(‘One   of   the top 5 baseball   players,  ever!’)
>>> if hits > 10 and shield == 0:
        print(‘You're   dead  …’)
>>> if north or south or east  or  west:
        print(‘I  can   escape.’)

3.3 The if statement in the interactive shell is shown without the result of the execution:

>>> if year % 4 == 0:
        print(‘Could   be  a  leap year.’)
    else:
        print(‘Definitely   not  a  leap year.’)
>>> if ticket == lottery:
        print(‘You won!’)
    else:
        print(‘Better   luck   next time…’)

3.4 List users is defined first. The id is then requested using function input(). The condition id in users is used in an if statement to determine the appropriate message:

users = [‘joe’, ‘sue’, ‘hani’, ‘sophie’]
id = input(‘Login: ’)
if id in users:
    print(‘You are in!’)
else:
    print(‘User unknown.’)
print(‘Done.’)

Figure 3.20 presents the flowchart describing the different execution flows of this program.

3.5 We use a for loop to iterate through the words in the list. For each word, we check whether it has length 4; if so, we print it.

wordList = eval(input(‘Enter word list: ’))
for word in wordList:
  if len(word) == 4:
    print(word)

image

Figure 3.20 Program flowchart. The solid arrows show the execution flow that always occurs. The dashed arrows show the possible execution flows that occur depending on a condition.

3.6 The for loops are:

>>> for i in range(10):
        print(i)
>>> for i in range(2):
        print(i)

3.7 We omit the complete for loop:

(a) range(3, 13), (b) range(0, 10, 2), (c) range(0, 24, 3), and (d) range(3, 12, 5).

3.8 The function average() takes two inputs. We use variable names x and y to refer to the input arguments. The average of x and y is (x+y)/2:

>>> def average(x, y):
        ‘returns average of x and y’
        return (x + y) / 2

3.9 The perimeter of a circle of radius r is 2 πr. The math function needs to be imported so the value math.pi can be obtained:

import math
def perimeter(radius):
    ‘returns perimeter of circle of given radius’
    return 2 *math.pi * radius

3.10 The function should iterate over all numbers in the list and test each to determine whether it is negative; if so, the number is printed.

def negatives(lst):
    ‘prints the negative numbers in list lst’
    for i in lst:
        if i < 0:
            print(i)

3.11 The docstrings are shown in the solutions of the respective Practice Problems.

3.12 When variable a is assigned 3, a is bound to the new object 3. Variable b is still bound to the list object.

image

3.13 The parallel assignment statement is the easiest way to achieve the swap:

>>> team[0], team[-1] = team[-1], team[0]

Another way would be to use a temporary variable temp:

>>> temp = team[0]
>>> team[0] = team[-1]
>>> team[-1] = temp

3.14 This function just wraps the swapping code we developed in the previous practice problem.

def swapFL(lst):
    lst[0], lst[-1] = lst[-1], lst[0]

3.15 The solution uses the jump() functions from module turtlefunctions we developed in the case study. In order for Python to import this module, it must be in the same folder as the module containing the olympic() function.

import turtlefunctions
def olympic(t):
    ‘has turtle t draw the olympic rings’
    t.pensize(3)
    jump(t, 0, 0)   # bottom of top center circle
    t.setheading(0)

    t.circle(100) # top center circle
    turtlefunctions.jump(t, -220, 0)
    t.circle(100) # top left circle
    turtlefunctions.jump(t, 220, 0)
    t.circle(100) # top right circle
    turtlefunctions.jump(t, 110, -100)
    t.circle(100) # bottom right circle
    turtlefunctions.jump(t, -110, -100)
    t.circle(100) # bottom left circle

Exercises

3.16 Use the eval() function to evaluate these strings as Python expressions:

  1. ‘2 * 3 + 1’
  2. ‘hello’
  3. ”‘hello’ + ‘ ’+ ‘world!’”
  4. “‘ASCII’.count(‘I’)”
  5. ‘x = 5’

Which evaluations result in an error? Explain why.

3.17 Assume a, b, and c have been defined in the interactive shell as shown:

>>> a, b, c = 3, 4, 5

Within the interactive shell, write if statements that print ‘OK’ if:

  1. a is less than b.
  2. c is less than b.
  3. The sum of a and b is equal to c.
  4. The sum of the squares a and b is equal to c squared.

3.18 Repeat the previous problem with the additional requirement that ‘NOT OK’ is printed if the condition is false.

3.19 Write a for loop that iterates over a list of strings lst and prints the first three characters of every word. If lst is the list [‘January’, ‘February’, ‘March’] then the following should be printed:

Jan
Feb
Mar

3.20 Write a for loop that iterates over a list of numbers lst and prints the numbers in the list whose square is divisible by 8. For example, if lst is [2, 3, 4, 5, 6, 7, 8, 9], then the numbers 4 and 8 should be printed.

3.21 Write for loops that use the function range() and print the following sequences:

  1. 01
  2. 0
  3. 3456
  4. 1
  5. 03
  6. 59131721

Problems

Note: In the programs that use interactive input of nonstring values, you will need to use the function eval() to force Python to treat the user's input as a Python expression (rather than just a string).

3.22 Implement a program that requests a list of words from the user and then prints each word in the list that is not ‘secret’.

>>>
Enter list of words: [‘cia’,‘secret’,‘mi6’,‘isi’,‘secret’]
cia
mi6
isi

3.23 Implement a program that requests a list of student names from the user and prints those names that start with letters A through M.

>>>
Enter list: [‘Ellie’, ‘Steve’, ‘Sam’, ‘Owen’, ‘Gavin’]
Ellie
Gavin

3.24 Implement a program that requests a nonempty list from the user and prints on the screen a message giving the first and last element of the list.

>>>
Enter a list: [3, 5, 7, 9]
The first list element is 3
The last list element is 9

3.25 Implement a program that requests a positive integer n from the user and prints the first four multiples of n:

>>>
Enter n: 5
0
5
10
15

3.26 Implement a program that requests an integer n from the user and prints on the screen the squares of all numbers from 0 up to, but not including, n.

>>>
Enter n: 4
0
1
4
9

3.27 Implement a program that requests a positive integer n and prints on the screen all the positive divisors of n. Note: 0 is not a divisor of any integer, and n divides itself.

>>>
Enter n: 49
1
7
49

3.28 Implement a program that requests four numbers (integer or floating-point) from the user. Your program should compute the average of the first three numbers and compare the average to the fourth number. If they are equal, your program should print ‘Equal’ on the screen.

>>>
Enter first number: 4.5
Enter second number: 3
Enter third number: 3
Enter last number: 3.5
Equal

3.29 Implement a program that requests the user to enter the x and y coordinates (each between 10 and 10) of a dart and computes whether the dart has hit the dartboard, a circle with center (0,0) and radius 8. If so, string It is in! should be printed on the screen.

>>>
Enter x: 2.5
Enter y: 4
It is in!

3.30 Write a program that requests a positive four-digit integer from the user and prints its digits. You are not allowed to use the string data type operations to do this task. Your program should simply read the input as an integer and process it as an integer, using standard arithmetic operations (+, *, -, /, %, etc).

>>>
Enter n: 1234
1
2
3
4

3.31 Implement function reverse_string() that takes as input a three-letter string and returns the string with its characters reversed.

>>> reverse_string(‘abc’)
‘cba’
>>> reverse_string(‘dna’)
‘and’

3.32 Implement function pay() that takes as input two arguments: an hourly wage and the number of hours an employee worked in the last week. Your function should compute and return the employee's pay. Any hours worked beyond 40 is overtime and should be paid at 1.5 times the regular hourly wage.

>>> pay(10, 10)
100
>>> pay(10, 35)
350
>> pay(10, 45)
475

3.33 The probability of getting n heads in a row when tossing a fair coin n times is 2n. Implement function prob() that takes a nonnegative integer n as input and returns the probability of n heads in a row when tossing a fair coin n times.

>>> prob(1)
0.5
>>> prob(2)
0.25

3.34 Implement function reverse_int() that takes a three-digit integer as input and returns the integer obtained by reversing its digits. For example, if the input is 123, your function should return 321. You are not allowed to use the string data type operations to do this task. Your program should simply read the input as an integer and process it as an integer using operators such as // and %. You may assume that the input integer does not end with the 0 digit.

>>> reverse_int(123)
321
>>> reverse_int(908)
809

3.35 Implement function points() that takes as input four numbers x1, y1, x2, y2 that are the coordinates of two points (x1, y1) and (x2, y2) in the plane. Your function should compute:

  • The slope of the line going through the points, unless the line is vertical
  • The distance between the two points

Your function should print the computed slope and distance in the following format. If the line is vertical, the value of the slope should be string ‘infinity’. Note: Make sure you convert the slope and distance values to a string before printing them.

>>> points(0, 0, 1, 1)
The slope is 1.0 and the distance is 1.41421356237
>>> points(0, 0, 0, 1)
The slope is infinity and the distance is 1.0

3.36 Implement function abbreviation() that takes a day of the week as input and returns its two-letter abbreviation.

>>> abbreviation(‘Tuesday’)
‘Tu’

3.37 The computer game function collision() checks whether two circular objects collide; it returns True is they do and False otherwise. Each circular object will be given by its radius and the (x, y) coordinates of its center. Thus the function will take six numbers as input: the coordinates x1 and y1 of the center and the radius r1 of the first circle, and the coordinates x2 and y2 of the center and the radius r2 of the second circle.

>>> collision(0, 0, 3, 0, 5, 3)
True
>>> collision(0, 0, 1.4, 2, 2, 1.4)
False

3.38 Implement function partition() that splits a list of soccer players into two groups. More precisely, it takes a list of first names (strings) as input and prints the names of those soccer players whose first name starts with a letter between and including A and M.

>>> partition([‘Eleanor’, ‘Evelyn’, ‘Sammy’, ‘Owen’, ‘Gavin’])
Eleanor
Evelyn
Gavin
>>> partition([‘Xena’, ‘Sammy’, ‘Owen’])
>>>

3.39 Write function lastF() that takes as input a string of the form ‘FirstName LastName’ and returns a string of the form ‘LastName, F.’. (Only the initial should be output for the first name.)

>>> lastF(‘John Locke’)
‘Locke, J.’
>>> lastF(‘Albert Camus’)
‘Camus, A.’

3.40 Implement function avg() that takes as input a list that contains lists of numbers. Each number list represents the grades a particular student received for a course. For example, here is an input list for a class of four students:

[[95, 92, 86, 87], [66, 54], [89, 72, 100], [33, 0, 0]]

The function avg should print, one per line, every student's average grade. You may assume that every list of grades is nonempty, but you may not assume that every student has the same number of grades.

>>> avg([[95, 92, 86, 87], [66, 54], [89, 72, 100], [33, 0, 0]])
90.0
60.0
87.0
11.0

3.41 The computer game function hit() takes five numbers as input: the x and y coordinates of the center and the radius of a circle C, and the x and y coordinates of a point P. The function should return True if point P is inside or on circle C and False otherwise.

>>> hit(0, 0, 3, 3, 0)
True
>>> hit(0, 0, 3, 4, 0)
False

3.42 Implement function ion2e() that takes a string as input and returns a copy of the word back with the following change: if the entered word ends in ‘ion’, then ‘ion’ is replaced with ‘e’.

>>> ion2e(‘congratulation’)
‘congratulate’
>>> ion2e(‘marathon’)
‘marathon’

3.43 Write a function distance() that takes as input a number: the time elapsed (in seconds) between the flash and the sound of thunder. Your function should return the distance to the lightning strike in kilometers. The speed of sound is approximately 340.29 meters per second; there are 1000 meters in one kilometer.

>>> distance(3)
1.0208700000000002
>>> distance(6)
2.0417400000000003

3.44 (This problem builds on Problem 2.28.) Implement function polygon() that takes a number n ≥ 3 as input and draws, using Turtle graphics, an n-sided regular polygon.

3.45 Using Turtle graphics, implement function planets(), which will simulate the planetary motion of Mercury, Venus, Earth, and Mars during one rotation of planet Mars. You can assume that:

  1. At the beginning of the simulation, all planets are lined up (say along the negative y-axis).
  2. The distances of Mercury, Venus, Earth, and Mars from the Sun (the center of rotation) are 58, 108, 150, and 228 pixels.
  3. For every 1 degree circular motion of Mars, Earth, Venus, and Mercury will move 2, 3, and 7.5 degrees, respectively.

The figure below shows the state of the simulation when Earth is about a quarter of the way around the Sun. Note that Mercury has almost completed its first rotation.

image

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset