⌂ Programmation
Fiche 11 sur 13

Répéter un nombre connu de fois

La boucle for, quand on sait combien de tours on veut.

Après cette fiche, vous saurez :

1Les trois éléments, rassemblés

À la fiche 10, toute boucle while avait besoin de trois choses : l'initialisation, la condition, et la modification.

int compteur = 1;              // 1. initialisation

while (compteur <= 5)          // 2. condition
{
    Console.WriteLine(compteur);
    compteur = compteur + 1;   // 3. modification
}

Le problème : ces trois éléments sont éparpillés. On oublie facilement le troisième, et la boucle tourne à l'infini.

La boucle for les rassemble sur une seule ligne.

for (int compteur = 1; compteur <= 5; compteur = compteur + 1)
{
    Console.WriteLine(compteur);
}
Ce que l'ordinateur affiche
1
2
3
4
5
PartieRôleQuand elle s'exécute
int compteur = 1Initialisationune seule fois, au départ
compteur <= 5Conditionavant chaque tour
compteur = compteur + 1Modificationaprès chaque tour

Les trois parties sont séparées par des points-virgules. Il y en a deux à l'intérieur des parenthèses, et aucun après la parenthèse fermante.

À retenir

Le raccourci i++

On écrit presque toujours la modification avec le raccourci vu à la fiche 5 :

for (int i = 1; i <= 5; i++)
{
    Console.WriteLine(i);
}

i++ veut dire i = i + 1. C'est identique, et c'est la forme que vous verrez partout.

Et pourquoi i ? C'est une habitude vieille de soixante ans : i comme index. Personne n'écrit compteur dans une boucle for.

2for ou while ?

forwhile
À utiliser quandon sait combien de tourson ne sait pas combien de tours
Exempleafficher les 12 mois de l'annéedemander jusqu'à ce que l'utilisateur tape « stop »
Le compteurgéré tout seul, sur une ligneà gérer soi-même, en trois endroits

À retenir

La question à se poser : est-ce que je connais le nombre de tours avant de commencer ?

Les deux fonctionnent toujours. Ce n'est qu'une question de lisibilité. Mais un for bien choisi rend le code beaucoup plus clair.

3Se servir de la variable de boucle

Le i n'est pas seulement un compteur. On peut s'en servir dans les calculs.

La table de multiplication

Console.Write("Table de quel nombre ? ");
int nombre = int.Parse(Console.ReadLine());

Console.WriteLine();

for (int i = 0; i <= 10; i++)
{
    Console.WriteLine($"{nombre} x {i} = {nombre * i}");
}
Ce que l'ordinateur affiche
Table de quel nombre ? 7

7 x 0 = 0
7 x 1 = 7
7 x 2 = 14
7 x 3 = 21
7 x 4 = 28
7 x 5 = 35
7 x 6 = 42
7 x 7 = 49
7 x 8 = 56
7 x 9 = 63
7 x 10 = 70

À retenir

Onze lignes affichées, une seule ligne écrite.

Sans boucle, il aurait fallu écrire onze Console.WriteLine presque identiques, en changeant un chiffre à chaque fois. Avec le risque d'en rater un.

Et si demain on veut aller jusqu'à 20, on change un seul caractère.

Compter à l'envers

for (int i = 10; i >= 1; i--)
{
    Console.WriteLine(i);
}

Console.WriteLine("Décollage !");

i-- est le contraire de i++ : il retire 1. Et la condition devient i >= 1.

Avancer de deux en deux

// Les nombres pairs de 0 à 20
for (int i = 0; i <= 20; i = i + 2)
{
    Console.WriteLine(i);
}

Rien n'oblige à avancer d'un seul cran.

4Cumuler dans une boucle

C'est l'usage le plus fréquent. On reprend le principe du total de la fiche 5, mais avec une boucle.

double total = 0;

for (int i = 1; i <= 3; i++)
{
    Console.Write($"Prix de l'article {i} : ");
    double prix = double.Parse(Console.ReadLine());

    total = total + prix;
}

Console.WriteLine();
Console.WriteLine($"Total à payer : {total:F2} euros");
Ce que l'ordinateur affiche
Prix de l'article 1 : 15,50
Prix de l'article 2 : 4,20
Prix de l'article 3 : 29,99

Total à payer : 49,69 euros

Attention

La variable qui cumule doit être déclarée AVANT la boucle.

// Faux
for (int i = 1; i <= 3; i++)
{
    double total = 0;      // remise à zéro à chaque tour !
    total = total + prix;
}

// Correct
double total = 0;
for (int i = 1; i <= 3; i++)
{
    total = total + prix;
}

Dans la version fausse, total est recréé et remis à zéro à chaque tour. Le résultat final ne contient que le dernier prix.

Et de toute façon, total n'existerait plus après la boucle : impossible de l'afficher.

La règle : ce qui doit survivre à la boucle se déclare avant elle.

Compter combien

int total = 0;
int nombreDeReponses = 0;

for (int i = 1; i <= 5; i++)
{
    Console.Write($"Note {i} : ");
    int note = int.Parse(Console.ReadLine());

    total = total + note;
    nombreDeReponses = nombreDeReponses + 1;
}

double moyenne = (double)total / nombreDeReponses;
Console.WriteLine($"Moyenne : {moyenne:F2}");

Attention

(double)total : rappel de la fiche 7.

total et nombreDeReponses sont deux int. Leur division serait entière, et la moyenne fausse.

L'écriture (double)total demande de traiter total comme un nombre à virgule le temps du calcul. On pourrait aussi écrire total / 5.0.

→Exercices

1Trois bouclesRecopier

Recopiez ces trois boucles et prédisez leur résultat avant de lancer.

// A
for (int i = 1; i <= 5; i++)
{
    Console.WriteLine($"A : {i}");
}

Console.WriteLine();

// B
for (int i = 5; i >= 1; i--)
{
    Console.WriteLine($"B : {i}");
}

Console.WriteLine();

// C
for (int i = 0; i <= 10; i = i + 5)
{
    Console.WriteLine($"C : {i}");
}

Console.ReadKey();

Solution

Ce que l'ordinateur affiche
A : 1
A : 2
A : 3
A : 4
A : 5

B : 5
B : 4
B : 3
B : 2
B : 1

C : 0
C : 5
C : 10

A monte de 1 à 5. C'est la forme la plus courante.

B descend. Notez que tout a changé : la valeur de départ, le sens de la comparaison (>=), et i-- au lieu de i++. Si vous n'en changez qu'un seul, la boucle ne tourne pas du tout ou tourne à l'infini.

C avance de 5 en 5. Trois tours seulement : 0, 5, 10. Au tour suivant i vaudrait 15, ce qui échoue au test.

À tester : dans B, remplacez i-- par i++. Que se passe-t-il ? Boucle infinie : i part de 5 et monte, donc i >= 1 reste vrai pour toujours.

2La table de multiplicationModifier

Reprenez la table de multiplication de la section 3.

  1. Faites-la aller jusqu'à 20 au lieu de 10.
  2. Ajoutez une ligne de séparation après le titre.
  3. Modifiez-la pour n'afficher que les résultats pairs de la table.
  4. Combien de lignes avez-vous dû changer pour la question 1 ?

Aide pour la 3 : un nombre est pair si le reste de sa division par 2 vaut zéro. En C# : resultat % 2 == 0.

Solution

Console.Write("Table de quel nombre ? ");
int nombre = int.Parse(Console.ReadLine());

Console.WriteLine();
Console.WriteLine($"=== TABLE DE {nombre} ===");
Console.WriteLine("---------------------");

for (int i = 0; i <= 20; i++)
{
    int resultat = nombre * i;

    if (resultat % 2 == 0)
    {
        Console.WriteLine($"{nombre} x {i} = {resultat}");
    }
}

Console.ReadKey();
Ce que l'ordinateur affiche
Table de quel nombre ? 7

=== TABLE DE 7 ===
---------------------
7 x 0 = 0
7 x 2 = 14
7 x 4 = 28
7 x 6 = 42
7 x 8 = 56
...

Réponse à la question 4 : une seule. Il a suffi de remplacer i <= 10 par i <= 20.

C'est tout l'intérêt de la boucle. Sans elle, il aurait fallu écrire dix Console.WriteLine supplémentaires.

Le symbole % s'appelle le modulo. Il donne le reste d'une division entière.

7 % 2   // 1  -> 7 divisé par 2 fait 3, il reste 1
8 % 2   // 0  -> 8 divisé par 2 fait 4, il reste 0

Un reste nul veut donc dire : la division tombe juste, le nombre est pair. C'est la façon standard de tester la parité, dans tous les langages.

Notez la combinaison boucle + condition : le if est à l'intérieur de la boucle. Il est testé à chaque tour.

3Le relevé de compteCréer

Écrivez un programme de gestion de dépenses.

  1. Demandez combien de dépenses l'utilisateur veut encoder.
  2. Pour chacune, demandez un libellé et un montant.
  3. Affichez chaque dépense au fur et à mesure, numérotée.
  4. À la fin, affichez le total, la dépense moyenne, et le nombre de dépenses.
  5. Si le total dépasse 500 euros, affichez un avertissement.

Solution

Console.Write("Combien de dépenses ? ");
int nombre = int.Parse(Console.ReadLine());

double total = 0;

Console.WriteLine();

for (int i = 1; i <= nombre; i++)
{
    Console.Write($"Libellé de la dépense {i} : ");
    string libelle = Console.ReadLine();

    Console.Write($"Montant                   : ");
    double montant = double.Parse(Console.ReadLine());

    total = total + montant;

    Console.WriteLine($"  -> {i}. {libelle} : {montant:F2} euros");
    Console.WriteLine();
}

double moyenne = total / nombre;

Console.WriteLine("+-----------------------------------+");
Console.WriteLine($"  Nombre de dépenses : {nombre}");
Console.WriteLine($"  Total              : {total:F2} euros");
Console.WriteLine($"  Dépense moyenne    : {moyenne:F2} euros");
Console.WriteLine("+-----------------------------------+");

if (total > 500)
{
    Console.WriteLine();
    Console.WriteLine("ATTENTION : votre budget de 500 euros est dépassé !");
    Console.WriteLine($"Dépassement : {total - 500:F2} euros");
}

Console.ReadKey();
Ce que l'ordinateur affiche
Combien de dépenses ? 3

Libellé de la dépense 1 : Courses
Montant                   : 245,80
  -> 1. Courses : 245,80 euros

Libellé de la dépense 2 : Essence
Montant                   : 78,50
  -> 2. Essence : 78,50 euros

Libellé de la dépense 3 : Électricité
Montant                   : 215,00
  -> 3. Électricité : 215,00 euros

+-----------------------------------+
  Nombre de dépenses : 3
  Total              : 539,30 euros
  Dépense moyenne    : 179,77 euros
+-----------------------------------+

ATTENTION : votre budget de 500 euros est dépassé !
Dépassement : 39,30 euros

Vérification : 245,80 + 78,50 + 215,00 = 539,30. Divisé par 3, cela fait 179,77. Prenez toujours cette habitude de contrôler le résultat de tête : une moyenne doit forcément se situer entre la plus petite et la plus grande valeur.

Pourquoi la moyenne est-elle correcte ici ? Parce que total est un double. La division total / nombre mélange donc un double et un int, ce qui suffit à obtenir des décimales — c'est la règle de la fiche 7.

Les trois points techniques :

  • total est déclaré avant la boucle, sinon il serait remis à zéro à chaque tour et n'existerait plus après.
  • libelle et montant sont déclarés dans la boucle : ils ne servent qu'au tour en cours.
  • Le i sert à numéroter l'affichage. C'est un usage typique de la variable de boucle.

Je sais faire

Une case qui coince ? Relisez la partie concernée avant de passer à la fiche suivante.

← Fiche 10 Fiche 12 : Les sous-programmes →