Semaine 1 · Jour 3 · 420-SN1

LES BOUCLES

Répéter sans se répéter : écrire une fois, exécuter autant qu'on veut
🧑‍🚀 EN SAVOIR PLUS · UN PEU D'HISTOIRE

La boucle bien avant Python

Ada Lovelace · 1843

Note G

Elle écrit le tout premier algorithme destiné à une machine (jamais construite) de Babbage. Sa « Note G » décrit une suite d'opérations répétée en cycle : en 1843, elle invente la première boucle.

Elle invente la programmation, près d'un siècle avant l'ordinateur : ses notes donnent déjà des exemples qui combinent des variables et des boucles - exactement ce qu'on apprend dans ce cours.

Les cartes perforées

Dès 1804, le métier à tisser de Jacquard enchaîne des cartes cousues en anneau pour répéter un motif. Le mot « boucle » vient de ce ruban refermé sur lui-même.

Jusqu'aux années 1960, un programme = un paquet de cartes en carton. Échappé par terre = tout dans le désordre. Aujourd'hui, range() fait ça sans une miette. 😅

La copie : 5 fois la même ligne

La consigne du prof : « Tu copies cette phrase 5 fois. » La copie de l'élève, en Python, ressemble à ça :

print("Je ne répéterai plus") print("Je ne répéterai plus") print("Je ne répéterai plus") print("Je ne répéterai plus") print("Je ne répéterai plus")

Copier-coller 5 fois, ça passe. Mais si la consigne était 1 000 fois ? Et si la phrase change ? On recopie 1 000 corrections ? Il y a mieux.

La même copie, avec une boucle de 1 à 5

for ligne in range(1, 6): print("Je me répète")
2 lignes remplacent les 5 d'avant - et feraient aussi bien 1 000 tours.

On écrit la ligne une seule fois, et la boucle la répète. range(1, 6) fait compter le compteur : 1, 2, 3, 4, 5. La borne de fin (6) n'est pas incluse : on s'arrête juste avant.

La même sortie, deux écritures

À LA MAIN 5 lignes recopiées
print("Je ne répéterai plus") print("Je ne répéterai plus") print("Je ne répéterai plus") print("Je ne répéterai plus") print("Je ne répéterai plus")
AVEC UNE BOUCLE 2 lignes
for ligne in range(1, 6): print("Je ne répéterai plus")

Exactement la même sortie à l'écran. À gauche on se répète ; à droite on écrit la ligne une fois et c'est range qui compte les tours. Plus le nombre de répétitions est grand, plus l'écart se creuse.

Anatomie d'une boucle « pour »

for ligne in range(1, 6): print(ligne) # bloc en retrait = répété à chaque tour
for … in
les mots-clés qui lancent la boucle
ligne
le compteur : une variable qui change à chaque tour
range(1, 6)
la suite de valeurs à parcourir : 1, 2, 3, 4, 5
: puis retrait
le bloc indenté est ce qu'on répète (comme au Jour 2)

range() : la suite de nombres du compteur

On écritLe compteur prendCombien de tours
range(5)0, 1, 2, 3, 45
range(1, 6)1, 2, 3, 4, 55
range(0, 10, 2)0, 2, 4, 6, 85
range(5, 0, -1)5, 4, 3, 2, 15

Deux réflexes Python : sans premier nombre, on part de 0 ; la borne de fin est exclue. Le 3e nombre est le pas (de combien on avance à chaque tour) : négatif, il fait compter à rebours (compte à rebours d'une fusée 🚀).

Le compteur n'est pas que décoratif

Le compteur existe dans le bloc : on l'affiche devant le texte pour numéroter. Même technique, deux usages :

for mouton in range(1, 6): print(mouton, "moutons")
1 moutons 2 moutons 3 moutons 4 moutons 5 moutons
for ligne in range(1, 6): print(ligne, "copie corrigée")
1 copie corrigée 2 copie corrigée 3 copie corrigée 4 copie corrigée 5 copie corrigée

La même boucle sert à compter des moutons ou à numéroter une copie : c'est print(compteur, ...) qui place le numéro devant le texte, sans rien recopier.

Un if DANS la boucle : le « s » du pluriel

À LA MAIN 5 fois
print("mouton") print("mouton") print("mouton") print("mouton") print("mouton")
EN BOUCLE numéroté
for numero in range(1, 6): print(numero, "moutons")
1 moutons ⚠️ 2 moutons 3 moutons
+ UN IF le « s » juste
for numero in range(1, 6): if numero == 1: print(numero, "mouton") else: print(numero, "moutons")
1 mouton ✅ 2 moutons 3 moutons

En boucle, « 1 moutons » est faux. On glisse une condition (Jour 2) DANS la boucle (Jour 3) : si le numéro vaut 1, on écrit « mouton », sinon « moutons ». La boucle décide, à chaque tour, du bon affichage.

Le fil du compteur, tour par tour

for mouton in range(1, 6): print(mouton, "moutons")
Tour
mouton
Le code déroulé
Ce qui s'affiche
1
1
print(1, "moutons")
1 moutons
2
2
print(2, "moutons")
2 moutons
3
3
print(3, "moutons")
3 moutons
4
4
print(4, "moutons")
4 moutons
5
5
print(5, "moutons")
5 moutons

À chaque tour, ligne prend la valeur suivante de range, puis le bloc s'exécute. Après 5, plus rien dans range : la boucle s'arrête.

Un accumulateur : partir d'un « effet nul »

Un accumulateur est une variable qui grossit à chaque tour. Sa valeur de départ ne doit rien fausser : on choisit celle qui ne change rien à l'opération.

ADDITION on part de 0
total = 0 for valeur in [2, 5, 3]: total = total + valeur print(total)
10
+ 0 ne change rien → départ 0
MULTIPLICATION on part de 1
produit = 1 for valeur in [2, 5, 3]: produit = produit * valeur print(produit)
30
× 1 ne change rien → départ 1

Le piège : initialiser le produit à 0 donnerait toujours 0 (tout × 0 = 0) ; et une somme partant de 1 serait décalée de 1. La bonne valeur de départ est l'élément neutre de l'opération : 0 pour +, 1 pour ×.

Et quand on ne sait pas combien de tours ?

for … in range(...)

POUR : le nombre de tours est connu d'avance (souvent : la taille des données)

for compteur in range(1, 6): print(compteur)
while condition

TANT QUE : on répète jusqu'à ce qu'une condition (Jour 2 !) devienne fausse

compteur = 1 while compteur <= 5: print(compteur) compteur = compteur + 1 # sinon, sans fin

Même sortie (1 à 5) : à gauche range connaît le nombre de tours ; à droite c'est toi qui fais avancer le compteur et qui dois penser à l'arrêt.

Un while piloté par une progression

temperature = 90 while temperature > 37: print("On refroidit…", temperature) temperature = temperature - 10 print("Prêt :", temperature)
On refroidit… 90 On refroidit… 80 On refroidit… 70 On refroidit… 60 On refroidit… 50 On refroidit… 40 Prêt : 30

La boucle teste une condition qui change à chaque tour. Impossible de deviner en lisant combien de tours : ça dépend de la température de départ. Dès que temperature > 37 devient faux, on sort.

Un while avec une variable drapeau 🚩

Un drapeau est une variable bool (Jour 2 !) qui dit « on continue ». Tant qu'il est levé (True), la boucle tourne ; on le baisse (False) pour l'arrêter.

drapeau = True compteur = 0 while drapeau: compteur = compteur + 1 print("tour", compteur) if compteur >= 3: drapeau = False # on baisse le drapeau
tour 1 tour 2 tour 3

Pratique quand l'arrêt dépend de plusieurs raisons : on baisse le drapeau n'importe où dans le bloc, et la boucle s'arrête au tour suivant.

⚠️ Danger : la boucle qui ne s'arrête jamais

Un while répète tant que sa condition est vraie. Si rien dans le bloc ne finit par la rendre fausse, la boucle tourne pour toujours et le programme se fige.

OUBLI compteur figé
compteur = 1 while compteur <= 5: print(compteur) # compteur reste 1 # 1 <= 5 toujours vrai ∞
DRAPEAU jamais baissé
drapeau = True while drapeau: print("encore") # on ne met jamais # drapeau = False ∞
CORRIGÉ ça évolue
compteur = 1 while compteur <= 5: print(compteur) compteur = compteur + 1 # un jour 6 > 5 : on sort

Règle d'or du while : à chaque tour, quelque chose doit rapprocher la condition du « faux » - faire avancer le compteur ou finir par baisser le drapeau. Et si un programme s'emballe : Ctrl + C l'arrête.

« pour » ou « tant que » : surtout un style

for … in range / données

Le nombre de tours est connu d'avance : il vient le plus souvent des données - 5 lignes, les 30 mesures d'un capteur, les éléments d'une liste.

for mesure in mesures: # autant de tours que de mesures
while condition

On répète tant qu'une condition tient. On l'écrit surtout quand le nombre de tours n'est pas connu d'avance : tant que l'usager n'a pas répondu, tant que l'écart dépasse le seuil.

while ecart > 0.01: # on ne sait pas en combien de tours

C'est surtout un style d'écriture, pas une loi : on pourrait connaître le nombre de tours et utiliser quand même un while. La vraie question : mes tours dépendent-ils d'une quantité de données (→ pour) ou d'une condition qui évolue (→ tant que) ?

Sortir ou sauter un tour : break et continue

break quitter la boucle
for nombre in range(1, 10): if nombre == 5: break print(nombre)
1 2 3 4
continue sauter ce tour
for nombre in range(1, 7): if nombre % 2 == 0: continue print(nombre)
1 3 5

break = quitter la boucle tout de suite (les tours restants sont abandonnés). continue = sauter au tour suivant sans finir le bloc. Les deux marchent avec for comme avec while.

À TOI DE JOUER

Dans ton calepin, devine la sortie avant d'exécuter :

range(1, 4) → ?
range(3) → ?
range(2, 11, 2) → ?
code.experimentations.xyz/calepins/jour-3-boucles/

AU TRAVAIL !

Séance 1-3 : écris une fois, laisse le compteur faire le reste
⤺ Refermer le diaporama