De « ça compile » à « je sais le lire »
Dans la page précédente, vous avez pris un fichier source et l'avez transformé en un programme exécutable à l'aide d'un compilateur. Maintenant, nous allons ralentir et regarder ce qu'il y avait réellement dans ce fichier. Tout programme C++ est construit à partir de la même poignée d'éléments structurels, et une fois que vous saurez les nommer, un fichier .cpp inconnu cessera de ressembler à du bruit.
Voici un programme complet et exécutable. Lisez-le une fois, puis nous le décortiquerons ligne par ligne.
Cinq lignes utiles, et chacune d'elles remplit un rôle précis. Passons-les en revue.
La ligne #include
#include <iostream>
Cette ligne intègre l'en-tête <iostream> afin que vous puissiez utiliser des fonctionnalités d'entrée/sortie comme cout. Le #include est une directive de préprocesseur : elle s'exécute avant la vraie compilation et colle en somme le contenu de cet en-tête dans votre fichier.
Deux choses rendent les lignes #include particulières :
- Elles commencent par
#, ce qui les marque comme directives de préprocesseur. - Elles ne se terminent pas par un point-virgule. C'est l'exception courante à l'habitude « chaque ligne se termine par
;» que vous êtes sur le point d'acquérir.
Si vous utilisez cout mais oubliez #include <iostream>, le compilateur ne saura pas ce qu'est cout et vous obtiendrez une erreur comme 'cout' was not declared in this scope. La solution est presque toujours un include manquant.
La fonction main
int main() {
// ...
return 0;
}
main est l'endroit où votre programme commence. Lorsque vous exécutez le programme compilé, l'exécution démarre à la première ligne à l'intérieur de main et s'arrête quand main retourne. Tout programme C++ possède exactement un main - ni plus, ni moins.
Les éléments :
int-mainrenvoie un entier au système d'exploitation. Par convention,0signifie « terminé avec succès ».main()- le nom, suivi de parenthèses pour ses paramètres (vides ici).{ ... }- les accolades enveloppent le corps : les instructions qui s'exécutent.return 0;- terminemainet signale le succès. Si vous l'omettez, le C++ traitemaincomme s'il avait retourné0à votre place, mais l'écrire rend votre intention évidente.
Les instructions et le point-virgule
Une instruction est une consigne complète. En C++, chaque instruction se termine par un point-virgule :
Le C++ ignore entièrement les sauts de ligne et les espaces supplémentaires. Le compilateur se moque que vous mettiez les instructions sur une ligne ou sur dix : c'est le ; qui lui indique où chaque instruction se termine. Ces trois formes sont identiques pour le compilateur :
int a = 1; int b = 2;
int a = 1;
int b = 2;
int
a
= 1;
Cette liberté s'accompagne du piège le plus fréquent chez les débutants : un point-virgule oublié. Regardez ce qui se passe ici.
int x = 5 // <-- pas de point-virgule
int y = 10;
Vous obtiendrez une erreur comme expected ';' before 'int'. Notez le piège : le compilateur ne se rend compte que quelque chose ne va pas qu'en atteignant la ligne suivante, si bien que le numéro de ligne signalé pointe souvent une ligne en dessous de la vraie erreur. Quand une erreur mentionne un ; manquant, vérifiez la ligne au-dessus de celle indiquée dans le message.
Les accolades définissent des blocs
Là où certains langages utilisent l'indentation pour regrouper le code, le C++ utilise les accolades { }. Tout ce qui se trouve entre une paire d'accolades correspondantes forme un bloc. Les corps de fonctions, les boucles et les instructions if en font usage :
Les deux lignes à l'intérieur des accolades du if ne s'exécutent que lorsque la condition est vraie. Le dernier cout est en dehors des accolades, il s'exécute donc toujours.
Comme ce sont les accolades - et non l'indentation - qui définissent la structure, le C++ ne vous oblige pas à indenter. Mais vous devriez le faire tout de même : l'indentation est la façon dont les humains lisent la structure que les accolades définissent. Un bug courant est une accolade non appariée - chaque { a besoin d'un } fermant. Si vous en oubliez un, le compilateur signale généralement une erreur près de la fin du fichier (expected '}' at end of input), loin de l'endroit où vous avez réellement dérapé. Compter vos accolades, ou laisser votre éditeur les apparier pour vous, évite bien des confusions.
La sortie avec cout et <<
Vous avez maintenant vu cout à plusieurs reprises. C'est le flux de sortie standard, et vous lui envoyez des valeurs avec l'opérateur << (lisez-le comme « mets ceci dans la sortie ») :
Vous pouvez enchaîner les << pour afficher plusieurs choses à la suite. endl termine la ligne (il vide aussi le tampon) ; la séquence d'échappement "\n" est une façon plus légère d'afficher un saut de ligne. Pour des programmes simples, l'une ou l'autre convient.
À propos de ce using namespace std; en haut : les noms de la bibliothèque standard se trouvent dans l'espace de noms std, le nom complet est donc std::cout. Écrire using namespace std; une fois vous permet d'omettre le préfixe std:: et d'écrire simplement cout. C'est pratique dans les petits exemples, mais dans les gros projets, beaucoup d'équipes préfèrent le std::cout explicite pour éviter les conflits de noms - ne soyez donc pas surpris de le voir écrit de l'une ou l'autre façon.
Vous savez maintenant lire le squelette de n'importe quel programme
Des includes en haut, une fonction main comme point d'entrée, des instructions se terminant par des points-virgules, des accolades regroupant le code en blocs et cout << pour la sortie - ce squelette se trouve dans presque tous les fichiers C++ que vous ouvrirez. Le reste du langage n'est que du détail posé par-dessus ces quelques formes. Quand un programme paraît intimidant, trouvez d'abord main, puis lisez les instructions dans l'ordre ; la structure vous guidera.
Suite : les commentaires
Pour l'instant, chaque ligne de vos programmes est du code que le compilateur lit. Ensuite, nous ajouterons des lignes qu'il ignore délibérément - les commentaires - afin que vous puissiez laisser des notes pour vous-même et pour les autres lecteurs. Vous verrez la forme sur une seule ligne // et la forme bloc /* ... */, ainsi que les cas où chacune est le bon choix.
Questions fréquentes
Pourquoi chaque instruction C++ a-t-elle besoin d'un point-virgule ?
Le C++ ignore les sauts de ligne et les espaces, il lui faut donc un marqueur explicite indiquant où une instruction se termine et où la suivante commence. Ce marqueur est le point-virgule ;. Un point-virgule oublié est l'erreur de compilation la plus fréquente chez les débutants, et le numéro de ligne signalé désigne souvent la ligne suivant celle où vous l'avez oublié.
Que fait int main() en C++ ?
main est la fonction par laquelle le programme commence à s'exécuter : l'exécution débute à sa première ligne et s'arrête lorsqu'elle retourne. Tout programme C++ a besoin d'exactement un main. Le int signifie qu'elle renvoie un code de statut entier au système d'exploitation, où 0 indique le succès par convention.
Suis-je obligé d'écrire std:: avant cout ?
Vous pouvez soit écrire std::cout (pleinement qualifié), soit ajouter using namespace std; une fois en haut puis écrire simplement cout. La forme qualifiée est plus sûre dans les gros fichiers ; using namespace std; est un raccourci courant dans les petits exemples et les tutoriels.