Article Index

Les conditions

Lors de la programmation, il est extrêmement important de contrôler le flux du code exécuté et dans quelle circonstance. Les commandes Python if elif else agissent comme un trafic numérique, vous permettant de définir des blocs de code qui s'exécutent lorsque certaines conditions sont remplies. Nous partons d’un exemple simple avec seulement le mot-clé if pour expliquer le fonctionnement de cette instruction et petit à petit, nous ajoutons des éléments, en particulier qui utilisent les mots-clés elif et else, pour montrer différentes possibilités. Cette exemple est le suivant :

if condition:
    print('Affichage si la valeur de la condition est vrai')

Nous notons quelques éléments de syntaxe de base, premierement l'instruction if ce situe devant, ensuite on ajoute une condition, puis un séparateur : permettant a python de comprendre la fin de la condition, la suite de code indenté apres la ligne if condition : est la parti qui seras exécuté si la condition est vrai. L'indentation est au choix du développeur (tabulation ou 4 espace) mais doit etre consitant dans tout le code, c'est ce que l'on appelle un contexte, dont les notions plus avancé seront développez plus tard ! Notons également qu'il est possible d'écrire la condition sur une seul ligne, s'il existe qu'une seul instruction a exécuté :

if condition: print('Affichage si la valeur de la condition est vrai')

Nous avons vu qu’un élément clé de l’instruction if est la condition associée, dont la valeur, vraie (True) ou fausse (False), est souvent le résultat de comparaisons entre valeurs. Donnons ici tous les opérateurs de comparaison, appelés opérateurs relationnels en python. Supposons que les variables a et b aient chacun une certaine valeur (par exemple a = 3 et b = 5). Les opérateurs de comparaisons, appelés dans le jargon informatique opérateurs relationnels, possibles sont :

condition vérité
a < b la valeur de a est-elle strictement inférieure à la valeur de b
a > b la valeur de a est-elle strictement supérieure à la valeur de b
a <= b la valeur de a est-elle inférieure ou égale à la valeur de b
a >= b la valeur de a est-elle supérieure ou égale à la valeur de b
a == b la valeur de a est-elle égale à la valeur de b
a != b la valeur de a est-elle différente de la valeur de b

Par exemple, supposons les variables i,j,k respectivement initialisées a 37,42,42,
la table de vérité associé a chaque opérateur relationnel est la suivante :

superieur superieur ou egal inferieur inferieur ou equale eguale non eguale
i > j → false i >= j → false i < j → true i <= j → true i == j → false i != j → true
j > i → true j >= i → true j < i → false j <= i → false k == j → true k != j → false
k > j → false k >= j → true k < j → false k <= j → true  i == k → false  i != k → true

Bien entendue nous pouvons combiner plusieurs condition avec d'autres opérateurs relationel de logique :

porte vérité python
not vrai si a faux not a
or vrai si un des deux est vrai a or b
and vrai si les deux sont vrai a and b
nor vrai si aucun ne l'est not (a or b)
nand faux si les deux sont vrai not (a and b)
xor vrai si les deux sont différent a != b
xand vrai si les deux sont identique a == b

Ainsi nous pouvons par exemple écrire le code suivant :

i,j,k = 36,42,42
if i>j or j==k:
    print('La condition est vrai')

En décomposant la condition comme fait python, cela donne la suite d'instruction suivante :

i,j,k = 36,42,42

condition = i<j or j==k
condition = 36<42 or 42==42
condition = False or 42==42
condition = False or True
condition = True

if condition:
    print('La condition est vrai')

Puisque dans notre cas la condition est vrai, le texte s'affichera ! Nous pouvons maintenant introduire le mot clés else, dont les éléments de syntaxe sont identique au if, mais ne contient pas de condition, en voici un exemple :

condition = False
if condition:
    print('La condition est vrai')
else:
    print('La condition est fausse')

En fait ce mots clés correspond a l'instruction "sinon" en francais, donc si la condition initiale est fausse, alors le code indenté défini apres le else seras éxécuté ! Ce qui est le cas dans cette exemple ! Pour aller un peu plus loin dans les conditions nous pouvons biensur les imbriquées, en utilisant l'indentation :

a = True
b = False
if a:
    if b:
        print('a vrai, b vrai')
    else:
        print('a vrai, b faux')
else:
    if b:
        print('a faux, b vrai')
    else:
        print('a faux, b faux')

Ce code simple peut devenir dans certain cas tres long, c'est ce que l'on appelle un anti pattern et plus exactement, l'imbrication des if peut generer un code en forme de fleche (nested if statements generate an arrow shape) ... Exemple PHP :

https://miro.medium.com/max/720/0*b3YTwb9y11fdUDpm.jpg

Pour éviter cela ont peut utiliser le mot clés elif ! Ainsi le code précédent devint :

a = True
b = False
if a and b:
    print('a vrai, b vrai')
elif a and not b:
    print('a vrai, b faux')
elif not a and b:
    print('a faux, b vrai')
else:
    print('a faux, b faux')

Si le premier test du if échoue, python passe au second test, au elif et ainsi de suite. Si tous les tests du if et des elif sont évalués à faux et qu’il n’y a pas de partie else (optionel) aucune « branche » du if ne sera exécutée ! Un bonne exemple de l'utilisation du if elif else est le calcule des racines d'un polynome d'ordre 2 :

import math

# demande sucessivement 3 floatant a l'utilisateur
a = float(input("a"))
b = float(input("b"))
c = float(input("c"))

# calcule de delata, attention l'operateur ** equivaut a l'exposant
delta = b**2 - 4*a*c

# si delta est proche de zero (valeur absolue < 1e-10)
# ce qui est possible en cas d'imprecission des calcule
if abs(delta) < 1e-10:
    # alors 1 solution reel
    print("solution unique", -b/(2*a))

# dans le cas contraire (delta != 0), si delta est positif
elif delta > 0:
    # alors 2 solution reel
    print("solution 1", (-b + math.sqrt(delta)) / (2*a))
    print("solution 2", (-b - math.sqrt(delta)) / (2*a))

# sinon delta est ni positif, ni nul, donc negatif
else:
    # alors pas de solution reel simple
    delta = abs(delta)
    s1 = complex(-b, math.sqrt(delta)) / (2*a)
    s2 = complex(-b, -math.sqrt(delta)) / (2*a)

    print("pas de solution reel: ")
    print("solution complex 1", s1)
    print("solution complex 2", s2)

    if abs(s1+s2).imag < 1e-10:
        print("somme des solutions complex": -b/a)

    if abs(s1*s2).imag < 1e-10:
        print("produit des solutions complex": c/a)

Pour aller plus loin sur les conditions, il faut s'intéréssé à la logique booléenne, je vous conseil de lire le cours de Tech Info et l'introduction de Roger Reynaud. Attention toute fois, les opérateurs utilisés en logique booléen sont différent. Par exemple le + correspond au or et le au and.


Les boucles while

Maintenant que vous maitrisez bien les conditions if elif else, nous allons voir les boucles ! en introduisant successivement les mots clés while break continue ! Les éléments de syntaxe du while sont tres proche du if, mais il faudra faire attention que la condition devient fausse a un moment donné de l'exécution, sinon le code boucleras indéfiniment ! aie ! Chaque passage dans la boucle est appelé une itération ... L'instruction while peut ce traduire en francais par "tant que" , donc tant que la condition est vrai, le code est exécuté, retourne au début et teste de nouveaux la condition, jusqu'a ce qu'elle devienne fausse.

while condition:
    print('code a executer')
    # modification qui influence la condition
    variable = ???

L'exemple le plus simple est une boucle qui qui affiche les entiers de 0 a 10 :

i = 0
while i<=10:
    print(i)
    i = i+1

Ici tant que i est inférieur ou égale a 10, ont affiche i et ont l'incrément de 1. Lors de la derniere itération, quand i vaut 10, le code est exécuté, affiche 10, incrément i qui vaut 11, retourne au début de la boucle. L'instruction while teste alors la condition qui est fausse et met fin a l'exécution de la boucle. L'execution et le comportement d'une boucle peu etre influencer par d'autre moyens que la condition intiale, grace aux instructions break et continue. Donnons un exemple de base simple :

i = 0

while True:
    i = i+1

    # i impaire ?
    if i%2 == 1: continue # aller au point 1
            
    print(i)
    
    if i>=10: break # sorti direct, au point 2

    # point 1 fin du code dans la boucle
    # puis retour a debut, teste de la condition, etc

#point 2 or de la boucle et suite du code
print('bla bla bla')

Pour la premiere, l'instruction continue permet de "casser" l'exécution du code a l'intérieur de la boucle en passant a la prochaine itération ! Dans cette exemple, i est incrémenté de 1 a chaque itération, lorsque i est impaire (premier if) alors l'instruction continue est exécuté qui amene le fils d'exécution au point 1 ce qui implique que la suite du code dans la boucle n'est pas exécuté, donc il n'y auras pas d'affichage et la seconde condition ne seras pas tester non plus, la suite du code n'est donc exécuté que lorsque i est paire ! La seconde instruction break permet de "casser" la boucle sans prendre en compte la condition initialement défini (ici tout le temps vrai), donc lorsque la second condition i>=10 est vrai, l'instruction break est exécuté et met fin a l'exécution de la boucle en allant au point 2 ! Ce code afficheras donc les entiers paires de 2 a 10 ! Ce dernier auras le meme comportement que le code suivant :

i = 2
while i<=10:
    print(i)
    i = i+2

Les instructions break et continue sont rarement utilisé, mais permettent dans certain cas, de grandement simplifier la logique du code, grace a un logique "divide and conquer" l'instruction break est par exemple utile lorsque l'on veut exécuter au moins une fois un tour de boucle, sans dupliquer le code, c'est le cas pour tester une entré utilisateur :

total = 0
while True:
    i = input()
    if i == 'F': break
    total = total+int(i)

Ne pas utiliser l'instruction break dans cette exemple reviendrai a écrire le code suivant :

total = 0
i = input()
while i != 'F':
    total = total+int(i)
    i = input()

Bref grace aux instruction if elif else while et break vous pouvez écrire votre premier petit jeux !

import random
NB_ESSAIS_MAX = 6
x = random.randint(0,100)
n = 0

while True:
    t = int(input())
    n = n+1
    if n == NB_ESSAIS_MAX: break
    elif t>x: print('Trop grand')
    elif t<x: print('Trop petit')
    else: break

if t == x: print('Gagné en', n, 'essais !')
else: print('Perdu ! Le secret était', x)

L'instruction continue est quand a elle plus utilisé conjointement a une boucle for que nous allons voir dans la section suivante, afin de "passé" les éléments indésirables d'une sequence.

Les boucles for

Pour simplifier l'écriture de certains codes, il existe les boucles for. Nous ne rentrerons pas ici dans le détail de sont utilisation, qui nécéssite la maitrise des notions d'iterateur. Que nous verrons dans le cour suivant. Ainsi, si nous reprenons un code simple du début :

i = 0
while i<=10:
    print(i)
    i = i+1

il peu s'écrire en 2 ligne avec une bouble for :

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

Ici, range est fait appel à la notions d'itérateur, a chaque tour de boucle l'objet renverra le chiffre suivant, de 0 à 9, une fois arrivé à 10 l'objet ne renverra rien et la boucle ce terminera simplement. Elle peu prendre 1,2 ou 3 arguments, par exemple :

# start(0) / end (10)
>>> [i for i in range(0,10)]
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

# start (0) / end(10) / step (2)
>>> [i for i in range(0,10,2)]
[0, 2, 4, 6, 8]

# end (10)
>>> [i for i in range(10)]
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

Cette notation est un peu particulière, et nous revoiendrons dessus plus tard