type(True)bool
In the previous tutorial, we mentioned – without detailing – the notion of conditional statements, through the example of membership tests. Now, we will delve into the details of how conditions work in Python. They are a major step in creating programs that automate operations since they allow you to execute or not execute code based on certain conditions. They enable the computer to make decisions based on criteria set by the user.
In its simplest form, a test in Python is an expression that evaluates to “true” or “false.” For example, the expression \(3 > 2\) is true, so the associated test will return “true.” For this type of evaluation, Python has a particular type of object: booleans. Unlike the object types we have seen (int, float, str, etc.), booleans can only take two values: True and False.
type(True)bool
Like any object, booleans can be assigned to variables.
a = False
print(a)
print(type(a))False
<class 'bool'>
The values True and False must be written precisely this way (first letter capitalized, no quotes). They also cannot be used as variable names to avoid ambiguities.
a = true # Python will look for the variable `true`, but it doesn't exist--------------------------------------------------------------------------- NameError Traceback (most recent call last) Cell In[51], line 1 ----> 1 a = true # Python will look for the variable `true`, but it doesn't exist NameError: name 'true' is not defined
True = 3Cell In[52], line 1 True = 3 ^ SyntaxError: cannot assign to True
Comparison operators formalize mathematical comparison operations (equality, inequality, inequalities). They compare two values and return a boolean value.
| |Let’s illustrate these operators with a few examples.
3 == 3True
63 == 36False
2 != 3True
2 != 2False
3 > 2True
a = 36
a <= aTrue
a < aFalse
Everything seems to work correctly for usual mathematical operations. But these operators actually work on any type of object.
'do re mi fa sol' == 'do re mi fa sol'True
'do re mi fa sol' == 'Do Re Mi Fa Sol'False
'duck' != 'bee'True
True == TrueTrue
True == FalseFalse
[1, 2, 3] == [1, 2, 3]True
[1, 2] != [3, 4]True
Finally, it is possible to chain comparisons. The expression returns True provided that each of the comparisons is true.
5 < 7 <= 8True
5 < 7 <= 6False
Boolean operators allow simultaneous testing of multiple logical expressions. Fundamentally, these operators take two boolean values as input and return a single boolean value according to fixed logic rules. These rules are stated in truth tables.
and operatorThe first boolean operator is and. Let’s look at its truth table:
| |True and True | True |True and False | False |False and True | False |False and False | False |Let’s verify these rules in practice with a few examples.
True and TrueTrue
False and TrueFalse
The rules seem to work on boolean values. Of course, in practice, we are more interested in evaluating real logical expressions. We can use these operators to test expressions that return a boolean value.
(3 > 2) and (5 <= 9)True
a = ("x" != "z")
b = ("x" == "y")
a and bFalse
Note the use of parentheses to delimit the tests: they are not mandatory but are strongly recommended as they greatly improve the readability of tests.
or operatorThe second boolean operator is or. Its truth table is as follows:
| |True or True | True |True or False | True |False or True | True |False or False | False |True or TrueTrue
False or TrueTrue
(3 > 2) or (5 <= 9)True
a = ("x" != "z")
b = ("x" == "y")
a or bTrue
not operatorThe last boolean operator is not. Its truth table is as follows:
| Expression | Evaluation |
|---|---|
not True |
False |
not False |
True |
not TrueFalse
not FalseTrue
not (3 + 3 == 6)False
not (7 < 7)True
All the expressions we have seen so far are boolean expressions: a test is performed, and the operation returns True or False depending on whether the evaluated expression is true or not. In the context of a computer program that automates operations, we want to use them as conditions: if the expression is true, then the computer must perform a certain operation. Conditional structures allow precisely this usage.
Let’s illustrate this principle by implementing the following program:
Define a variable x.
If x is greater than \(5\), then print “The expression is true.”
Otherwise, print “The expression is false.”
Vary the value of x to verify the correct operation of the test.
x = 7
if x >= 5:
print("The expression is true.")
else:
print("The expression is false.")The expression is true.
The previous example illustrates the syntax of conditional structures in Python. These structures are based on instruction blocks, which delimit the set of instructions to be executed when a test is true. Conditional structures have three rules:
The line specifying the test ends with :.
All instructions that must be executed if the test is true are at the same level of indentation.
The conditional structure ends when the indentation returns to its original level.
Note that conditional structures can indeed be nested, as illustrated in the following example.
x = 7
if x >= 5:
print("The first expression is true.")
if x >= 12:
print("The second expression is true.")The first expression is true.
When x = 7, the first test returns True, so the instruction block at indentation level 1 is executed line by line. The second test returns False, so the instruction block at indentation level 2 is not executed.
Vary the value of x so that both blocks are executed.
if, else, and elif statementsIn conditional structures, tests can be specified using three statements: if, else, and elif. The previous examples have already illustrated the operation of the first two (and most frequent) statements.
In the case of a simple test (a single condition), only an if statement will be used, whose operation is simple: if the condition (test) returns True, then the instruction block (indented) that follows is executed. If the condition returns False, nothing happens. Let’s illustrate this with a membership test, for which we have seen examples in the previous tutorial.
client = "Isidore"
if client in ["Alexandrine", "Achille", "Colette"]:
print("Known client.")In practice, we often want to specify an alternative when the condition of the if statement returns False. The else statement allows specifying an alternative instruction block.
client = "Isidore"
if client in ["Alexandrine", "Achille", "Colette"]:
print("Known client.")
else:
print("Unknown client.")Unknown client.
Finally, we may want to specify multiple alternatives. In this case, we will use elif statements. The first elif statement will only execute if the test of the if statement returns False. The second elif statement will only execute if the test of the first elif statement returns False, and so on. Again, a final else statement can be specified, which only executes if none of the previous tests returned True.
client = "Isidore"
if client == "Alexandrine":
print("Hello Alexandrine.")
elif client == "Achille":
print("Hello Achille.")
elif client == "Colette":
print("Hello Colette.")
else:
print("Hello dear unknown.")Hello dear unknown.
NB: The previous instructions are for example purposes only. In practice, there are much more concise ways to code a program that performs the same operations.
1/ What is the particularity of booleans compared to other basic object types in Python?
2/ What are the inputs and outputs of a comparison operator?
3/ What types of objects can be compared using a comparison operator?
4/ What is the difference between the = operator and the == operator?
5/ What are the inputs and outputs of a boolean operator?
6/ Explain in English the principle of the and boolean operator. Same for or and not.
7/ What is the difference between a boolean expression and a condition?
8/ What is the structure of a conditional statement?
9/ Can conditional statements be nested?
10/ Among the if, else, and elif statements, which ones are mandatory and which ones are optional?
1/ They have only two values: True and False. Other types have an infinite number of possible values.
2/ Inputs: two values. Output: boolean value.
3/ All types of objects. In practice, however, it often does not make much sense to compare objects of different types; the result will generally be False.
4/ The = operator assigns a value to a variable. The == operator tests the equality of two objects.
5/ Inputs: two boolean values or two expressions that return booleans. Output: boolean value.
6/ The and operator returns True if both of its inputs are True, and False in all other cases. The or operator returns True if at least one of its inputs is True, and False if both are False. The not operator returns False if its input is True, and True otherwise.
7/ In both cases, they are tests. A condition is when the expressions are used within conditional structures.
8/ The conditional statement starts with an if, else, or elif statement, ending with :. Then comes an indented instruction block that only executes if the statement is True. The block ends when the indentation returns to its original level.
9/ Yes, conditional statements can be nested indefinitely (in theory). Just be careful to respect the levels of indentation.
10/ Only the if statement is mandatory.
Predict the results of the following tests and verify your predictions:
'Simon' in ['simon', 'oceane', 'veronique']
[1, 2, 3] == ['1', '2', '3']
'x' != 'x'
(9 > 5) and (3 == 5)
(3 > 2 and 5 >= 1) or (5 <= 9 and 6 > 12)
not (9 > 2*3)
not (9 > (2*3))
not ((7 > 8) or (5 <= 5))
(True and True) or (True == False)
(not False) or (not True)
# Test your answer in this cell'Simon' in ['simon', 'oceane', 'veronique'] : False
[1, 2, 3] == ['1', '2', '3'] : False
'x' != 'x' : False
(9 > 5) and (3 == 5) : False
(3 > 2 and 5 >= 1) or (5 <= 9 and 6 > 12) : True
not (9 > 2*3) : False
not (9 > (2*3)) : False
not ((7 > 8) or (5 <= 5)) : False
(True and True) or (True == False) : True
(not False) or (not True) : True
Consider the program written in the following cell.
x = 10
if True:
print("Initialization.")
l = []
if x > 8:
l.append("a")
elif x >= 2:
l.append("b")
else:
l.append("c")
if x - 6 < 0:
print("Negative.")
print(l)Initialization.
['a']
For the following values:
x = 1
x = 5
x = 10
predict the program’s results:
What is l at the end of the program?
What is printed in the console during the program?
Verify your results.
# Test your answer in this cellx = 1 : l = ['c'] and messages printed: ‘Initialization’ and ‘Negative’
x = 5 : l = ['b'] and messages printed: ‘Initialization’ and ‘Negative’
x = 10 : l = ['a'] and messages printed: ‘Initialization’
Write a program that performs the following operations:
Define a list that contains 4 names.
Write a test that prints the message (‘Too many people.’) if the list contains more than three people.
Remove a person from the list (using the del function or the pop method seen in a previous tutorial).
Perform the test again, there should be no output.
# Test your answer in this cellpeople = ["Romuald", "Ursula", "Jean-Vincent", "Philomène"]
if len(people) > 3:
print('Too many people.')
print(people)
people.remove("Jean-Vincent")
print(people)
if len(people) > 3:
print('Too many people.')Too many people.
['Romuald', 'Ursula', 'Jean-Vincent', 'Philomène']
['Romuald', 'Ursula', 'Philomène']
The input function allows the user to enter a value in a Python program. The syntax is as follows: x = input(). When this command is executed, the user must enter a value, which is then assigned to the variable x.
Using input and the if, elif, and else statements, code the following program:
Ask the user for a value, which will be stored in a variable p.
If p is strictly less than $15, print the message “too low!”.
If p is strictly greater than $15, print the message “too high!”.
If p is equal to $15, print the message “right on!”.
Note, input returns a string by default. Therefore, you need to convert the value of p to an integer (using the int function) for the game to work.
# Test your answer in this cellp = input()
p = int(p)
if p < 15:
print("too low!")
elif p > 15:
print("too high!")
else:
print("right on!")--------------------------------------------------------------------------- StdinNotImplementedError Traceback (most recent call last) Cell In[92], line 1 ----> 1 p = input() 2 p = int(p) 4 if p < 15: File /opt/hostedtoolcache/Python/3.10.15/x64/lib/python3.10/site-packages/ipykernel/kernelbase.py:1281, in Kernel.raw_input(self, prompt) 1279 if not self._allow_stdin: 1280 msg = "raw_input was called, but this frontend does not support input requests." -> 1281 raise StdinNotImplementedError(msg) 1282 return self._input_request( 1283 str(prompt), 1284 self._parent_ident["shell"], 1285 self.get_parent("shell"), 1286 password=False, 1287 ) StdinNotImplementedError: raw_input was called, but this frontend does not support input requests.
In Python, all objects evaluate to True or False in a conditional test (if/else). The general rule is that objects that are zero or empty (e.g., an empty list, an empty dictionary) evaluate to False, and vice versa. But there is no need to know these rules by heart: they can be easily found in practice! For example, you can use the following conditional test:
if "test":
print("True.")
else:
print("False.")True.
Predict which boolean value the following objects will evaluate to, and verify using the previous syntax.
0
1
12
-1
’’ (empty string)
’ ’ (string containing only a space)
[] (empty list)
[''] (list containing only an empty string)
{}
{-1}
# Test your answer in this cell0 : False
1 : True
12 : True
-1: True
'' (empty string): False
' ' (string containing only a space): True
[] (empty list): False
[''] (list containing only an empty string): True
{}: False
{-1}: True
We have seen that it is possible to perform chained comparisons, which return True provided that each of the included comparisons is true. Find a way to rewrite the following chained comparison using boolean operators.
5 < 7 <= 8 < 18
# Test your answer in this cellprint(5 < 7 <= 8 < 18)
print(5 < 7 and 7 <= 8 and 8 < 18)True
True
A chained comparison can be rewritten with and operators. It makes sense: each comparison must be true for the whole to be true. In practice, the version with and is probably preferable for readability.
Booleans are strongly linked to binary language, where `1
corresponds to "true" and0` to “false.” Let’s see if this link exists in the context of Python. To do this:
Calculate the “integer representation” of the boolean value of your choice using the int function.
Use booleans in the context of mathematical calculations to verify their behavior in this context.
# Test your answer in this cellprint(int(True)) 1
A boolean evaluated as an integer indeed gives the associated binary value.
print(True + 3) 4
What do inequality comparison tests applied to strings return? Produce some examples to test the behavior.
# Test your answer in this cellprint("a" > "b")
print("a" < "b")
print("apricot" > "avocado")
print("apricot" < "avocado")
print("1" > "2")
print("1" < "2")
print("A1" < "A2")False
True
False
True
False
True
True
The order relation used is alphanumeric order: each character is taken individually, and the orders are A < Z and 1 < 9.
Equality tests between real numbers (type float in Python) can be misleading. To convince yourself, perform the following test: (6 - 5.8) == 0.2
To understand the test result, perform the calculation of the left-hand side of the test alone. What do you notice?
Imagine (without necessarily implementing it) another test, based on inequalities, that would allow testing approximate equality.
# Test your answer in this celldiff = 3 - 2.7
print(diff == 0.3)
print(diff)False
0.2999999999999998
In Python, floating-point numbers are always approximate values. We can therefore have such surprises in calculations.
tolerance = 0.0001
new_test = (0.3 - tolerance) < diff < (0.3 + tolerance)
print(new_test)True