Vue d'ensemble
Le langage C est le langage impératif de référence en MP2I. Impératif signifie qu'on décrit une suite d'instructions exécutées dans l'ordre, en modifiant des cases mémoire appelées variables. Dans cette première fiche, tu vas écrire ton premier programme, manipuler les types de base, afficher des valeurs, et surtout comprendre le piège n°1 des débutants en C : la division entière, où ne vaut pas mais .
#include, int main(void), return 0;) · types int, char, double, bool · déclaration et affectation, typage statique · affichage printf et formats %d %f %c · opérateurs + - * / % et division entière · conditions if / else · boucles for et while.
Prérequis
- Aucun prérequis de programmation : cette fiche part de zéro.
- Notions d'algorithmique utiles : la notion de variable, de boucle et de condition (au niveau intuitif).
- Savoir qu'un programme se lit de haut en bas, ligne après ligne.
Le C se dompte par la pratique. Les premières erreurs de compilation découragent vite ; un accompagnement ciblé fait gagner des semaines. Nos mentors alumni X · Centrale · Mines décryptent ton premier code avec toi, ligne par ligne.
Trouver un mentor →1. La structure d'un programme C
Tout programme C exécutable contient une fonction spéciale, main, qui est le point de départ. Voici le squelette minimal, le fameux « Bonjour ».
#include <stdio.h>
int main(void) {
printf("Bonjour, MP2I !\n");
return 0;
}#include <stdio.h>Charge la bibliothèque standard d'entrées/sorties (standard input/output). Sans elle, printf serait inconnu du compilateur. Le # indique une directive traitée avant la compilation.int main(void) {Déclare la fonction main, exécutée en premier. int annonce qu'elle renverra un entier ; (void) qu'elle ne prend aucun argument ; l'accolade { ouvre le bloc d'instructions.printf("Bonjour, MP2I !\n");Affiche le texte à l'écran. \n est le retour à la ligne (un seul caractère, pas deux). Le point-virgule final termine l'instruction : il est obligatoire.return 0;Termine main en renvoyant 0 au système, ce qui signifie « tout s'est bien passé ». Une valeur non nulle signalerait une erreur.}Ferme le bloc de main. À chaque { correspond exactement un }.On compile puis on exécute (par exemple avec gcc) :
// En terminal :
// gcc bonjour.c -o bonjour
// ./bonjour
// Sortie affichee :
// Bonjour, MP2I !gcc bonjour.c -o bonjourLe compilateur gcc traduit le fichier source bonjour.c en un exécutable nommé bonjour (option -o pour output)../bonjourLance l'exécutable. Le ./ précise « dans le dossier courant ». La sortie s'affiche alors dans le terminal.; — un oubli provoque une erreur de compilation souvent signalée à la ligne suivante, ce qui déroute. De même, toute { ouverte doit être refermée par }.
2. Types de base et variables
Une variable est une case mémoire nommée qui contient une valeur. En C, chaque variable a un type fixé à la déclaration : c'est le typage statique. Une variable déclarée int restera int pour toute sa vie ; on ne peut pas y ranger un texte.
Une variable est un nom associé à une zone mémoire et à un type (déterminé une fois pour toutes à la déclaration) qui fixe la nature des valeurs qu'elle peut contenir et la place qu'elle occupe. Déclarer réserve la case ; affecter (avec =) y range une valeur.
| Type | Contenu | Exemple de valeur | Format printf |
|---|---|---|---|
int | entier relatif | -3, 0, 42 | %d |
double | nombre à virgule (flottant) | 3.14, -0.5 | %f |
char | un caractère | 'A', 'z', '?' | %c |
bool | booléen (vrai/faux) | true, false | %d (0 ou 1) |
#include <stdio.h>
#include <stdbool.h>
int main(void) {
int age = 18;
double moyenne = 15.5;
char initiale = 'M';
bool admis = true;
printf("%d %f %c %d\n", age, moyenne, initiale, admis);
return 0;
}#include <stdbool.h>Nécessaire pour disposer du type bool et des valeurs true / false. Sans cet en-tête, ces mots seraient inconnus.int age = 18;Déclare la variable age de type int ET l'affecte à 18 en une ligne. Le type est désormais figé.double moyenne = 15.5;Un double stocke les nombres à virgule. On écrit un point décimal 15.5, jamais une virgule.char initiale = 'M';Un char contient un seul caractère, entre apostrophes simples 'M'. Les guillemets doubles "M" désigneraient un texte, ce qui est différent.bool admis = true;Un booléen vaut vrai ou faux. En interne true vaut 1 et false vaut 0.printf("%d %f %c %d\n", ...);Chaque %… est remplacé, dans l'ordre, par une variable : %d→age, %f→moyenne, %c→initiale, %d→admis.Sortie affichée : 18 15.500000 M 1. Remarque : %f affiche six décimales par défaut, et admis (booléen vrai) s'affiche en 1.
%.2f arrondit à deux décimales : printf("%.2f", 15.5) affiche 15.50. Le nombre après le point fixe le nombre de décimales voulues.3. Afficher avec printf
printf reçoit une chaîne de format contenant du texte et des marqueurs (%d, %f, %c…), suivis des valeurs à insérer. La règle d'or : le marqueur doit correspondre au type de la valeur.
#include <stdio.h>
int main(void) {
int points = 20;
double prix = 4.5;
char note = 'B';
printf("J'ai %d points.\n", points);
printf("Prix : %.2f euros\n", prix);
printf("Note : %c\n", note);
return 0;
}printf("J'ai %d points.\n", points);%d est remplacé par la valeur entière points (20). Le reste du texte est affiché tel quel.printf("Prix : %.2f euros\n", prix);%.2f affiche le flottant prix avec deux décimales : 4.50.printf("Note : %c\n", note);%c affiche un unique caractère, ici B.Sortie :
// J'ai 20 points.
// Prix : 4.50 euros
// Note : BJ'ai 20 points.%d a été remplacé par 20 ; le \n a provoqué le passage à la ligne suivante.Prix : 4.50 eurosDeux décimales imposées par %.2f.Note : BLe caractère seul, sans apostrophes (celles-ci n'existent que dans le code source).double avec %d (ou l'inverse) donne un résultat faux et imprévisible, sans forcément d'erreur bloquante. Vérifie toujours l'accord marqueur ↔ type.
4. Opérateurs et division entière
Les opérateurs arithmétiques sont + (addition), - (soustraction), * (multiplication), / (division) et % (reste, dit modulo). La priorité usuelle s'applique : *, /, % avant + et -. Ainsi 1 + 2 * 3 vaut , pas .
Quand les deux opérandes de / sont des entiers, le résultat est la division euclidienne : on garde le quotient entier, la partie décimale est supprimée (troncature vers zéro). L'opérateur % donne alors le reste. Pour et b>0 entiers, avec 0 \le a\%b < b.
#include <stdio.h>
int main(void) {
printf("%d\n", 7 / 2); // division entiere
printf("%d\n", 7 % 2); // reste
printf("%.1f\n", 7.0 / 2); // division flottante
return 0;
}7 / 2Deux entiers : division entière. , on garde le quotient 3 (le est jeté).7 % 2Le reste de cette même division euclidienne : 1. Très utile pour tester la parité (n % 2 == 0 ⇔ pair).7.0 / 2Dès qu'un opérande est un flottant (7.0), la division devient flottante : le résultat est 3.5. C'est la différence cruciale.Sortie affichée :
// 3
// 1
// 3.53Résultat de 7 / 2 : quotient entier.1Résultat de 7 % 2 : reste.3.5Résultat de 7.0 / 2 : la présence de 7.0 a activé la division flottante.7.0 / 2, 7 / 2.0, ou convertis avec un cast (double)a / b. Écrire double x = 7 / 2; range malgré tout 3.0 : le calcul entier a lieu avant le rangement dans le double.
n = 253 : n % 10 donne le chiffre des unités (3) et n / 10 retire ce chiffre (25). Le couple / 10 et % 10 permet de parcourir un nombre chiffre par chiffre.
La division entière piège encore en deuxième année. Nos mentors alumni X · Centrale · Mines t'entraînent sur les vrais réflexes (cast, parité, extraction de chiffres) pour que ça devienne une seconde nature.
Trouver un mentor →5. Conditions : if, else if, else
Une condition exécute un bloc seulement si un test est vrai. Le test utilise les comparateurs == (égal), != (différent), <, >, <=, >=.
#include <stdio.h>
int main(void) {
int note = 12;
if (note >= 16) {
printf("Tres bien\n");
} else if (note >= 10) {
printf("Admis\n");
} else {
printf("Insuffisant\n");
}
return 0;
}if (note >= 16) {Teste si note vaut au moins 16. Ici note vaut 12 : faux, on saute ce bloc.} else if (note >= 10) {Testé seulement si le précédent était faux. est vrai : ce bloc s'exécute.printf("Admis\n");Affiche Admis. Dès qu'une branche s'exécute, les suivantes sont ignorées.} else {Branche par défaut, exécutée si tous les tests précédents sont faux. Ici elle est ignorée.Sortie : Admis.
= n'est pas ==. = affecte une valeur ; == compare. Écrire if (note = 10) range 10 dans note et rend le test toujours vrai (10 ≠ 0). Le test d'égalité s'écrit if (note == 10).
6. Boucles for et while — exemple central
Une boucle répète un bloc. La boucle for convient quand on connaît le nombre de tours ; la boucle while quand on répète tant qu'une condition tient.
La boucle for : somme des entiers de 1 à n
Voici l'algorithme central de la fiche : calculer en accumulant dans une variable somme.
#include <stdio.h>
int main(void) {
int n = 5;
int somme = 0;
for (int i = 1; i <= n; i++) {
somme = somme + i;
}
printf("Somme de 1 a %d = %d\n", n, somme);
return 0;
}int n = 5;Fixe la borne : on veut .int somme = 0;L'accumulateur, initialisé à 0 : élément neutre de l'addition. On y ajoutera chaque entier.for (int i = 1; i <= n; i++) {Trois parties séparées par ; : initialisation i = 1 (une fois), condition i <= n (testée avant chaque tour), incrément i++ (après chaque tour, ajoute 1 à i).somme = somme + i;Le cœur : la nouvelle valeur de somme est l'ancienne plus i. On lit d'abord la droite, puis on range dans la gauche.}Fin du corps de boucle : on repart à la condition i <= n.printf(... n, somme);Après la boucle, affiche le résultat accumulé.Déroulons l'exécution pas à pas pour .
| Tour | i | i <= 5 ? | somme avant | somme = somme + i |
|---|---|---|---|---|
| 1 | 1 | vrai | 0 | 0 + 1 = 1 |
| 2 | 2 | vrai | 1 | 1 + 2 = 3 |
| 3 | 3 | vrai | 3 | 3 + 3 = 6 |
| 4 | 4 | vrai | 6 | 6 + 4 = 10 |
| 5 | 5 | vrai | 10 | 10 + 5 = 15 |
| 6 | 6 | faux → sortie | 15 | résultat : 15 ✓ |
Sortie affichée : Somme de 1 a 5 = 15. On retrouve bien .
La boucle while : même calcul, autre écriture
#include <stdio.h>
int main(void) {
int n = 5;
int somme = 0;
int i = 1;
while (i <= n) {
somme = somme + i;
i = i + 1;
}
printf("%d\n", somme);
return 0;
}int i = 1;Avec while, le compteur doit être déclaré avant la boucle (le for le faisait dans sa parenthèse).while (i <= n) {Répète le bloc tant que la condition est vraie. Elle est testée avant chaque tour.somme = somme + i;Même accumulation que dans le for.i = i + 1;Crucial : on incrémente à la main. L'oublier ⇒ i reste à 1, la condition reste vraie, boucle infinie.Sortie : 15. Le for et le while font ici exactement la même chose : le for regroupe juste init / condition / incrément en une seule ligne.
- Choisir un accumulateur et l'initialiser au neutre :
0pour une somme,1pour un produit. - Décider des bornes du compteur et de la condition d'arrêt (
i <= n?i < n?). - Dans le corps, mettre à jour l'accumulateur avec la valeur courante.
- Vérifier que le compteur progresse vers l'arrêt (sinon boucle infinie).
- Utiliser l'accumulateur après la boucle.
while, si rien ne fait avancer la condition vers le faux (compteur non incrémenté), le programme tourne sans fin. Toujours s'assurer qu'un pas rapproche de l'arrêt.
7. Exercices corrigés
Que produit exactement ce programme ? Justifie chaque ligne d'affichage.
#include <stdio.h>
int main(void) {
int n = 23;
printf("%d\n", n / 10);
printf("%d\n", n % 10);
printf("%d\n", n % 2);
return 0;
}Voir la correction détaillée
n / 10 : division entière de 23 par 10. , quotient 2.n % 10 : reste de la même division, soit 3 (le chiffre des unités).n % 2 : reste de 23 par 2. , reste 1 ⇒ 23 est impair.2, 3, 1.Écris un programme qui compte, avec une boucle for, combien d'entiers de 1 à 20 (inclus) sont multiples de 3, puis affiche ce nombre. Donne aussi la valeur affichée.
Voir la correction détaillée
k % 3 == 0.#include <stdio.h>
int main(void) {
int compte = 0;
for (int k = 1; k <= 20; k++) {
if (k % 3 == 0) {
compte = compte + 1;
}
}
printf("%d\n", compte);
return 0;
}compte initialisé à 0 (neutre du comptage) ; on l'incrémente à chaque multiple.6.Écris un programme calculant (produit ) pour n = 5 avec une boucle while. Trace l'évolution des variables et donne la valeur finale.
Voir la correction détaillée
produit initialisé à 1 (neutre de la multiplication, pas 0 !).#include <stdio.h>
int main(void) {
int n = 5;
int produit = 1;
int i = 1;
while (i <= n) {
produit = produit * i;
i = i + 1;
}
printf("%d\n", produit);
return 0;
}120. Piège évité : initialiser produit à 0 aurait donné 0 partout.Récap final — Ce qu'il faut absolument retenir
Ce premier contact avec le C pose les réflexes de base. Vérifie que tu maîtrises chacun de ces points avant de passer aux tableaux et aux fonctions.
- Sais-tu écrire le squelette minimal d'un programme (
#include,int main(void),return 0;) et le compiler ? - Sais-tu citer les quatre types de base et leur marqueur
printf(%d,%f,%c) ? - Sais-tu que le typage est statique : le type d'une variable est fixé à la déclaration ?
- Sais-tu pourquoi
7 / 2vaut 3 et7.0 / 2vaut 3.5 ? - Sais-tu à quoi sert
%(modulo) et comment tester la parité d'un entier ? - Sais-tu distinguer
=(affectation) de==(comparaison) ? - Sais-tu écrire une boucle
foret la traduire enwhileéquivalente ? - Sais-tu initialiser un accumulateur (0 pour une somme, 1 pour un produit) et éviter la boucle infinie ?