Skip to content

Sequence

Learning Objectives

At the end of this sub-unit, students should

  • understand how sequence of statement works.
  • know how to simplify complex operations into a sequence of simple operations.

Top Down

Currently, we implicitly assume that the execution of Python code is top down. This is true in general and we will discuss differences later on. But as a general rule, that is correct.

Python Sequence

Python program is executed line by line from top to bottom.

We use the term "line" rather loosely as a statement may involve multiple lines. Even a single expression may be written in multiple lines although that will involve the use of \ at the end of the line as shown below.

1
2
3
x = (1 + 2) * \
    (3 + 4)
# here, x is 21

Still, the general idea remains and we will use the term "line". Even so, as we see, a line may modify the state of the program especially if the line is an assignment statement. Next, a group of statements involving 1 or more lines may be called a block. You can refer to the basic terminology section of the appendix.

  • Expression


    x ** (y ** z)
    
  • Statement


    w = x ** (y ** z)
    
  • Block


    w = x ** (y ** z)
    u = w * w
    
  • Notes


    Block consists of one or more statements. Statement also includes expression.

Readable Code

Since programs are executed from top to bottom, the order of operations can be made clearer when written as several lines instead of a single line. Consider the quadratic formula.

\[x = \dfrac{-b \pm \sqrt{b^2 - 4ac}}{2a}\]

which is actually two formulas in disguise

\[x_1 = \dfrac{-b + \sqrt{b^2 - 4ac}}{2a} \ \ \text{and} \ \ x_2 = \dfrac{-b - \sqrt{b^2 - 4ac}}{2a}\]

For simplicity, we will assume that our program will start with the variables a, b, and c initialized accordingly via input() or otherwise. Additionally, we will assume that the chosen a, b, and c will have solutions.

How can we translate the formula into a code and assign the result into variable x1 and x2? With some deliberation, you may arrive at the following code with a very generous amount of parentheses to ensure the order of operations are maintained.

Quadratic Formula

x1 = (-b + ((b * b) - (4 * a * c)) ** 0.5)/(2 * a)
x2 = (-b - ((b * b) - (4 * a * c)) ** 0.5)/(2 * a)
Quadratic Formula

The following code is incorrect because of incorrect order of operation. In particular, we will divide by 2 and multiply by \(a\) instead of dividing by \(2a\).

x1 = (-b + ((b * b) - (4 * a * c)) ** 0.5)/ 2 * a
x2 = (-b - ((b * b) - (4 * a * c)) ** 0.5)/ 2 * a

This is why if you are unsure, simply put parentheses to ensure the correct order of operation.

That is a perfectly good solution. A short two lines code that solve our problem. However, it is not exactly readable and it has quite a number of duplicated operations. How can we improve?

First, note that we often call the \(b^2 - 4ac\) the discriminant. So we can actually try to compute that separately.

discriminant = (b * b) - (4 * a * c)

Secondly, the denominator is prone to error because we may accidentally write it without parentheses as ... / 2 * a. It will be nice to actually compute the denominator before using them.

denominator = 2 * a

Finally, we can combine them into a single more readable code at the expenses of more lines1. Additionally, there is going to be fewer issues with order of operation because the operations are on different lines with a clear order of operation.

Readable Quadratic Formula

1
2
3
4
5
6
# Assume a, b, and c are initialized
discriminant = (b * b) - (4 * a * c)
denominator = 2 * a

x1 = (-b + (discriminant ** 0.5)) / denominator
x2 = (-b - (discriminant ** 0.5)) / denominator

Even better, the computation of discriminant and denominator is performed only once. Generally, we want to do that: compute once, use multiple times.

Summary

Before we close this sub-unit, let us leave you with the following quote to motivate you on writing readable code.

Quote

"Always code as if the guy who ends up maintaining your code will be a violent psychopath who knows where you live. Code for readability."

John Woods

Summary

So to recap, although we may be able to solve the problem in as few lines as possible, it is often beneficial to rewrite the code into multiple lines to increase readability. This can be achieved by "lifting" the sub-expressions. The lifting process involve the following two steps.

  1. Replacing the sub-expression \(E\) with a variable name \(V\).
  2. Assigning the sub-expression \(V\) into the variable \(V\) (i.e., V = E).

Another advantage is that we may be able to reduce overall comptation as we may compute once and use multiple times.


  1. Of course, if you are using dis instead of discriminant and den instead of denominator, you may actually be writing shorter code at the expense of readability.