## Introduction Le premier contact avec un nouveau langage se fait traditionnellement par la création d'un programme affichant le message "Hello, World!". Dans ce chapitre, nous allons adapter ensemble le célèbre "Hello World" pour explorer les concepts fondamentaux de la structure d'un programme en C, de sa compilation et de son exécution. --- ## 1. Un Programme minimal en C : "Hello, UniLaSalle!" Voici le code source du programme "Hello, UniLaSalle!" en C. Nous allons l'analyser ligne par ligne. > [!example] Code source : hello.c > ```c > #include <stdio.h> >int main() { > /* Ceci est la fonction principale du programme. > Elle affiche un message à l'écran. */ > printf("Hello, UniLaSalle!\n"); > return 0; // Pour indiquer que le programme s'est terminé avec succès. } > ``` ## 2. Décortiquons le Code Chaque ligne de ce petit programme a une signification précise. Comprendre ces éléments est la clé pour écrire des programmes plus complexes. ### 2.1. La Directive de Préprocesseur `#include` La première ligne de notre programme est une **directive de préprocesseur**. > [!definition] Préprocesseur > Le préprocesseur est un programme qui s'exécute *avant* la compilation du code source. Il effectue des transformations textuelles sur le code, comme l'inclusion de fichiers, la substitution de macros, etc. * `#include` indique au préprocesseur d'inclure le contenu d'un autre fichier dans le fichier courant. > [!note] `stdio.h` `<stdio.h>` est le nom du fichier à inclure. `stdio` est l'abréviation de "Standard Input/Output Header". C'est un fichier d'en-tête standard de la bibliothèque C qui contient les déclarations des fonctions de gestion des entrées/sorties, comme `printf()` (pour afficher du texte) et `scanf()` (pour lire des entrées clavier). Sans cette ligne, le compilateur ne saurait pas ce qu'est `printf()` et générerait une erreur. > [!note] Différence entre `<...>` et `"..."` > * `<fichier.h>` : Indique au préprocesseur de chercher le fichier d'en-tête dans les répertoires standards du système (où sont installées les bibliothèques C). > * `"fichier.h"` : Indique au préprocesseur de chercher le fichier d'en-tête d'abord dans le répertoire courant du projet, puis dans les répertoires standards. C'est utilisé pour vos propres fichiers d'en-tête. Directives vs. Instructions Il est crucial de bien distinguer les **directives de préprocesseur** des **instructions**. | Caractéristique | Directive de Préprocesseur (`#include`) | Instruction (`printf`, `return`) | | :------------------- | :-------------------------------------------------------------------- | :-------------------------------------------------------------------- | | **Début** | Commence par `#` | Ne commence pas par `#` | | **Traitement** | Traitée par le **préprocesseur** avant la compilation | Traitée par le **compilateur** | | **Terminaison** | Ne se termine généralement PAS par un `;` (sauf rares exceptions) | DOIT se terminer par un `;` | | **Exemple** | `#include <stdio.h>` | `printf("Hello!\n");` <br> `int x = 10;` <br> `return 0;` | | **Rôle** | Prépare le code source pour le compilateur (inclusion de fichiers, macros) | Exécute une action spécifique lors de l'exécution du programme | ### 2.2. La Fonction Principale `main()` ```c int main() { // ... corps de la fonction ... return 0; } ``` * `main` : C'est le nom de la **fonction principale** de votre programme. Chaque programme C doit avoir une fonction `main()`. C'est le point d'entrée unique de l'exécution du programme : lorsque vous lancez votre exécutable, c'est cette fonction qui est appelée en premier. * `int` : C'est le **type de retour** de la fonction `main()`. Cela signifie que la fonction `main()` renverra un entier. Par convention, un retour de `0` (zéro) indique que le programme s'est terminé avec succès, tandis qu'une valeur non nulle indique une erreur. * `()` : Les parenthèses après `main` indiquent qu'il s'agit d'une fonction. Elles peuvent contenir des arguments (des informations passées à la fonction), mais pour l'instant, nous utilisons la forme simple sans arguments, parfois écrite `int main(void)`. * `{}` : Les **accolades** délimitent le Bloc de code le **corps de la fonction**. Tout le code entre l'accolade ouvrante `{` et l'accolade fermante `}` appartient à la fonction `main()` et sera exécuté lorsque la fonction sera appelée. > [!definition] Bloc de Code > Un bloc de code est un ensemble d'instructions regroupées. En C, les blocs de code sont délimités par des accolades `{}`. > [!note] La fonction `main` > La fonction `main` est le cœur de votre programme C. C'est là que l'exécution commence et se termine. ### 2.3. Les Commentaires : `/* ... */` et `// ...` Les commentaires sont des portions de texte ignorées par le compilateur. Leur rôle est d'expliquer le code, de le rendre plus lisible et compréhensible pour les humains (vous-même ou d'autres développeurs). En C, il existe deux types de commentaires : * **Commentaires sur une seule ligne** : Ils commencent par `//` et s'étendent jusqu'à la fin de la ligne. ```c // Ceci est un commentaire sur une seule ligne. int a = 10; // La variable 'a' stocke la valeur 10. ``` * **Commentaires multi-lignes** : Ils commencent par `/*` et se terminent par `*/`. Ils peuvent s'étendre sur plusieurs lignes. ```c /* * Ceci est un commentaire * qui s'étend sur * plusieurs lignes. */ ``` > [!tip] Bonne pratique > Commentez votre code de manière judicieuse. Un bon commentaire explique *pourquoi* le code fait quelque chose, plutôt que *ce que* le code fait (ce qui devrait être évident à la lecture du code lui-même). ### 2.4. L'Instruction `printf()` ```c printf("Hello, UniLaSalle!\n"); ``` * `printf()` : C'est une **fonction** de la bibliothèque standard C (déclarée dans `stdio.h`) dont le rôle est d'afficher du texte (ou des valeurs formatées) sur la **sortie standard** (généralement la console ou le terminal). * `"Hello, UniLaSalle!\n"` : C'est une **chaîne de caractères littérale** (une séquence de caractères) qui est passée en argument à la fonction `printf()`. * `Hello, UniLaSalle!` est le message que nous voulons afficher. * `\n` est une **séquence d'échappement** spéciale qui représente un retour à la ligne ("n" comme "***N**ew line*"). Sans elle, le curseur resterait sur la même ligne après l'affichage du message. > [!tip] Séquences d'échappement courantes > * `\n` : Nouvelle ligne > * `\t` : Tabulation horizontale > * `\\` : Caractère backslash > * `\"` : Caractère guillemet double ### 2.5. Le Point-Virgule `;` ```c printf("Hello, UniLaSalle!\n"); return 0; ``` Remarquez le point-virgule `;` à la fin de chaque ligne d'instruction. En C, le point-virgule est un **terminateur d'instruction**. Il indique au compilateur la fin d'une instruction. C'est un peu comme le point à la fin d'une phrase en français. > [!warning] Erreur fréquente > Oublier un point-virgule est une erreur très courante pour les débutants et peut entraîner des messages d'erreur de compilation parfois déroutants. ### 2.5. Le retour de fonction `return 0;` Cette instruction termine l'exécution de la fonction `main` et renvoie la valeur `0` au système d'exploitation. > [!note] Code de retour > * `return 0;` : Indique que le programme s'est exécuté avec succès. > * `return <valeur_non_nulle>;` : Indique que le programme s'est terminé avec une erreur. La valeur peut parfois donner une indication sur le type d'erreur. ## 3. Du Code Source à l'Exécutable : La Chaîne de Compilation Vous avez écrit votre code source dans un fichier (par exemple, `hello_world.c`). Comment cet ensemble de caractères devient-il un programme que votre ordinateur peut lancer ? C'est le rôle de la **chaîne de compilation**. > [!definition] Chaîne de Compilation > La chaîne de compilation est l'ensemble des étapes et des outils qui transforment le code source écrit dans un langage de programmation de haut niveau (comme le C) en un programme exécutable par la machine. Voici les étapes principales : 1. **Code Source** (`.c`) : Le fichier que vous écrivez (ex: `hello.c`). 2. **Préprocesseur** : Traite les directives (comme `#include`). Il génère un fichier temporaire où les inclusions sont effectuées, les macros remplacées, etc. 3. **Compilateur** : Traduit le code préprocessé en **code objet** (ex: `hello.o`). Le code objet est du code machine, mais il n'est pas encore un programme exécutable complet car il peut manquer des références à des fonctions de bibliothèques externes. 4. **Éditeur de Liens (Linker)** : Relie le code objet de votre programme avec les codes objets des fonctions de la bibliothèque standard (comme `printf` de `stdio.h`) et d'autres bibliothèques nécessaires. Il produit un **fichier exécutable** (ex: `hello` ou `hello.exe`). 5. **Exécution** : Le système d'exploitation charge le fichier exécutable en mémoire et commence son exécution à partir de la fonction `main()`. > [!note] Le compilateur GCC > `gcc` (GNU Compiler Collection) est un compilateur C très populaire et largement utilisé. Les commandes que vous avez vues plus tôt (`gcc hello.c -o hello`) orchestrent toutes ces étapes automatiquement. ## 4. Directives vs Instructions : Une Distinction Cruciale Maintenant que nous avons vu les éléments de base, formalisons la différence entre une directive et une instruction. C'est une distinction fondamentale pour comprendre comment le code C est traité. > [!definition] Directive de Préprocesseur > Une **directive de préprocesseur** est une commande destinée au préprocesseur C. Elle commence toujours par le symbole `#`. Elle est traitée *avant* la phase de compilation et modifie le code source lui-même (par exemple, en incluant d'autres fichiers). Les directives ne sont pas terminées par un point-virgule. > [!definition] Instruction > Une **instruction** est une commande destinée au compilateur. Elle représente une action à exécuter par le programme *pendant son exécution*. Les instructions font partie du code C "réel" et sont généralement terminées par un point-virgule `;`. Voici un tableau comparatif pour récapituler : | Caractéristique | Directive de Préprocesseur (`#include`) | Instruction (`printf();`) | | :----------------- | :-------------------------------------- | :-------------------------------------------- | | **Quand est-elle traitée ?** | Avant la compilation (par le préprocesseur) | Pendant la compilation (par le compilateur) et exécutée à l'exécution | | **Par qui est-elle traitée ?** | Le préprocesseur | Le compilateur et le processeur (runtime) | | **Symbole distinctif** | Commence par `#` | Se termine par `;` (généralement) | | **Exemple** | `#include <stdio.h>` | `printf("Hello!\n");` `return 0;` | | **Effet** | Modifie le code source avant compilation | Définit une action à exécuter à l'exécution du programme | > [!warning] Ne pas confondre > Confondre directives et instructions est une source d'erreurs et d'incompréhensions. Une directive ne sera jamais exécutée au runtime ; elle prépare le code pour la compilation. ## 5. Comment tester ce code ? Vous pouvez tester le code ci-dessus - en ligne sur [onlineGdb](https://www.onlinegdb.com/) par exemple si vous ne vous voulez/pouvez rien installer. - avec votre IDE favori (qui fera les appels au compilateur pour vous). > [!note] Environnement de Développement Intégré (IDE) > Dans un environnement de développement intégré (comme VS Code avec des extensions C/C++, Code::Blocks, CLion), la compilation et l'exécution sont souvent automatisées par un simple clic sur un bouton "Build" ou "Run". Cependant, comprendre les étapes sous-jacentes est fondamental. - "à la dure" si vous avez gcc (GNU Compiler Collection) installé sur votre ordinateur: > [!example] Comment utiliser gcc ? > 1. Enregistrez ce code dans un fichier nommé `hello.c` (l'extension `.c` est importante). > 2. Ouvrez un terminal ou une invite de commande. > 3. Compilez le programme avec un compilateur C (par exemple `gcc`) : > `gcc hello.c -o hello` > 4. Exécutez le programme : > `./hello` (sur Linux/macOS) ou `hello.exe` (sur Windows) > >Le `./` indique au système d'exécuter le programme situé dans le répertoire courant. >Vous devriez voir s'afficher : > ``` > Hello, UniLaSalle! > ``` --- ## Conclusion Félicitations ! Vous avez écrit, compilé et exécuté votre premier programme en C. Cette adaptation du "Hello, World!" est bien plus qu'un simple rite de passage ; il vous a introduit aux éléments fondamentaux de la syntaxe C : * Les directives de préprocesseur (`#include`) * Les commentaires (`/* */`, `//`) * La fonction principale (`main`) * Les blocs de code (`{}`) * Une fonction (`printf()`) * Une instruction (`return`) * Le terminateur d'instruction (`;`) * La distinction cruciale entre les **directives** (traitées par le préprocesseur avant l'exécution du programme) et les **instructions** (exécutées après lancement du programme). Ce programme minimal vous a déjà introduit à la structure de base d'un programme C et au cycle de compilation. Dans les prochains chapitres, nous construirons sur ces bases pour explorer des concepts plus complexes.