Section courante

A propos

Section administrative du site

Programmation avec Turbo C

Voici les étapes de bases pour pour écrire votre premier programme avec l'environnement de Turbo C.

Créer votre programme

La tradition veut que votre premier programme C soit toujours le programme Hello, world (Bonjour) trouvé dans l'ouvrage classique, The C Programming Language de Kernighan et Ritchie. Pour commencer, vous pouvez taper (à partir du prompt DOS) la commande suivante :

tc bonjour.c

Vous verrez apparaître une application ressemblant à ceci :

Il vous permet d'accéder à la version de l'environnement de développement intégré (IDE) de Turbo C, de créer un fichier nommé BONJOUR.C (s'il n'existe pas déjà) et de vous mettre dans l'éditeur Turbo C. Maintenant, tapez le programme suivant :

  1. main() {
  2.    printf("Bonjour!\n");
  3. }

Une fois entré dans ce programme, vous devez l'enregistrer sur le disque avant d'aller plus loin; après tout, si vous plantez votre système informatique, vous n'aimeriez pas perdre tout ce travail. Pour enregistrer votre premier programme Turbo C sur le disque, vous pouvez appuyer sur la touche F2 ou vous pouvez sélectionner Save dans le menu File en appuyant sur F10, F, S.

Compiler

Après avoir enregistré ce programme, vous devez faire deux choses avant de pouvoir l'exécuter : compilez-le puis liez-le. Pour compiler votre fichier, vous appuyez sur Alt+F9 (maintenez les touches enfoncé Alt et F9 en même temps). Une deuxième façon de compiler votre fichier est de retourner explicitement au menu principal (appuyez sur F10), sélectionnez C pour accéder au menu Compiler, puis appuyez à nouveau sur C (pour Compile to OBJ). Lorsque la compilation est terminée (ce qui ne devrait prendre qu'une seconde ou deux), un message clignotant à l'écran indiquera :

Success: Press any key

Lorsque vous appuyez sur une touche, la fenêtre disparaît et votre barre de menus est active. Si vous avez eu des avertissements ou des erreurs, ils apparaîtront dans la fenêtre Message en bas de l'écran. Vous ne devriez pas en avoir; donc si vous le faites, assurez-vous que vous avez tapé le programme exactement comme indiqué, puis compilez-le à nouveau.

Exécuter

Une fois que vous avez compilé sans aucune erreur, vous êtes prêt à exécuter votre programme. Puisque les menus sont actifs, vous pouvez simplement appuyer sur R (pour Run). Si vous êtes retourné dans l'éditeur, vous pouvez appuyer sur Alt+R; ou vous pouvez à nouveau afficher les menus (appuyez sur F10), puis appuyez sur R pour sélectionner la commande Run. Une nouvelle fenêtre de liaison apparaîtra, vous montrant que Turbo C est maintenant lié à toutes les routines de bibliothèque dont il a besoin.

Avez-vous des erreurs ? Si vous l'avez fait, c'est probablement parce que vous n'avez pas indiqué à Turbo C où se trouvent les fichiers de la bibliothèque. Si vous voyez toujours la fenêtre Linking, faites-la disparaître (appuyez sur n'importe quelle touche), appuyez sur F10 puis sur 0 pour afficher le menu Options (ou utilisez le raccourci clavier Alt+O). Appuyez sur E pour sélectionner la commande Environment, puis appuyez sur L pour choisir la commande Library de la bibliothèque. Lorsque la fenêtre du répertoire de la bibliothèque apparaît, saisissez le chemin d'accès complet du sous-répertoire où vous avez entreposé vos fichiers de bibliothèque - c'est probablement A:\TURBOC\LIB ou C:\TURBO\LIB - et appuyez sur Enter. Appuyez sur Esc pour faire disparaître le menu Environment, puis appuyez sur S (pour les options Store). Une boîte de prompt de fichier de configuration apparaîtra, avec le nom TCCONFIG.TC dedans. Appuyez simplement sur Enter; si Turbo C vous demande si vous souhaitez écraser TCCONFIG.TC, tapez la touche Y. Enfin, appuyez sur Esc pour faire disparaître le menu Options et appuyez sur la touche R pour recommencer.

À ce stade, le Turbo C devrait réussir à lier votre programme. Il signifie que pour que votre programme exécute des copies Turbo C dans les sous-programmes nécessaires à partir des bibliothèques d'exécution. Le modèle de mémoire par défaut est Small, donc Turbo C se liera dans les routines de bibliothèque de CS.LIB. Après avoir lié votre programme, le Turbo C l'exécute. L'écran s'efface, le message Bonjour! apparaît en haut de l'écran et le message Press any key to return to Turbo C... apparaît en bas. Appuyez sur n'importe quelle touche et l'écran Turbo C réapparaît.

Qu'est-il arrivé ?

Maintenant, sortez de Turbo C et regardez ce que vous avez créé. Sélectionnez la commande Quit dans le menu File. Dans le prompt DOS, tapez la commande suivante :

dir bonjour.*

et appuyez sur la touche Enter. Vous obtiendrez une liste de fichiers ressemblant à ceci :

BONJOUR.C 42 1-01-80 9:25p
BONJOUR.OBJ 221 1-01-80 9:26p
BONJOUR.EXE 4486 1-01-80 9:26p

Le premier fichier, BONJOUR.C, contient le texte (le code source) de votre programme. Vous pouvez l'afficher à l'écran; entrez simplement (au prompt DOS) la commande suivante :

type bonjour.c

Comme vous pouvez le voir, ce n'est pas très gros - seulement 42 octets de long. Le deuxième fichier, BONJOUR.OBJ, contient les instructions binaires de la machine (le code objet) produites par le compilateur Turbo C. Si vous utilisez la commande TYPE de DOS pour afficher ce fichier à l'écran, vous obtiendrez principalement du charabia. Le dernier fichier, BONJOUR.EXE, est le programme exécutable réel produit par Turbo Linker. Il contient non seulement le code dans BONJOUR.OBJ, mais également toutes les routines de support nécessaires (telles que printf) que l'éditeur de liens a copiées à partir du fichier de bibliothèque. Pour exécuter n'importe quel fichier exécutable, il vous suffit de taper son nom au prompt DOS, sans l'extension .EXE. Au prompt DOS, tapez bonjour et appuyez sur Enter. Le message Bonjour! apparaîtra à l'écran et le prompt DOS reviendra. Vous avez maintenant écrit un programme Turbo C fonctionnel que vous pouvez donner à tous vos amis.

Modification de votre premier programme Turbo C

Revenez dans Turbo C en tapant la commande suivante :

tc bonjour.c

Vous vous retrouverez dans l'éditeur Turbo C, avec votre programme déjà chargé. Vous allez maintenant le modifier pour pouvoir interagir un peu avec lui. Modifiez votre programme pour qu'il ressemble maintenant à ceci :

  1. main() {
  2.  char name[30];
  3.  printf("Quel est votre nom?");
  4.  scanf("%s",name);
  5.  printf("Bonjour, %s\n",name);
  6. }

Vous avez ajouté trois lignes à votre programme. La première ligne (char name[30];) déclare une variable nommée name, pouvant contenir une chaîne de 29 caractères maximum (lettre, chiffre, ponctuation,...). La deuxième ligne ajoutée appelle printf pour écrire le message Quel est votre nom?. La troisième ligne ajoutée appelle scanf pour lire votre nom dans le nom de la variable.

Enregistrez votre programme modifié en appuyant sur F2 ou F10, F, S. Appuyez sur F10 pour appeler le menu principal, puis appuyez sur R (pour Run). Notez que Turbo C est suffisamment intelligent pour savoir que vous avez modifié votre programme, il recompile donc le programme avant de l'exécuter.

Cette fois, lorsque votre programme s'exécute, trois choses se produisent : l'écran s'efface, le message Quel est votre nom? apparaît en haut et le curseur attend après le point d'interrogation. Tapez votre nom et appuyez sur Enter. Le programme dit maintenant Bonjour, votre_nom. Notez qu'il ne lit que le prénom que vous avez saisi. Appuyez sur n'importe quelle touche du clavier pour revenir à Turbo C.

Lorsque vous écrivez des programmes, vous pouvez faire des erreurs ou recevoir des avertissements. Une erreur est une erreur dans votre programme empêchant Turbo C de créer du code objet. Un avertissement n'est que cela: un message pour signaler un problème éventuel. Les erreurs et les avertissements sont répertoriés dans la fenêtre Message.

Envoi de votre sortie à une imprimante

Vous vous demandez comment envoyer votre programme "Bonjour" à une imprimante plutôt qu'à l'écran ? Nous allons vous montrer comment ici. Modifiez votre programme pour qu'il ressemble à ceci :

  1. #include <stdio.h>
  2. main () {
  3.  FILE *printer;
  4.  printer = fopen("PRN", "W");
  5.  fprintf(printer,"Bonjour!\n");
  6.  fclose(printer);
  7. }
  8.  
  9. /* Remarque : Si votre système utilise LPT1 ou LPT2, vous pouvez remplacer PRN par l'un ou l'autre pour spécifier votre imprimante. */    

Notez que cette fois nous avons utilisé la fonction fprintf au lieu de printf, et le programme a été préfacé avec une directive #include.

Écrire votre deuxième programme Turbo C

Modifiez maintenant votre programme pour en créer un nouveau. Entrez dans la fenêtre d'édition (appuyez sur F10 E ou Alt+E) et modifiez votre programme pour qu'il ressemble à ceci :

  1. main() {
  2.  int a,b,sum;
  3.  printf("Entrez deux nombres : ");
  4.  scanf("%d %d",&a,&b);
  5.  sum = a + b;
  6.  printf("La somme de %d \n",sum);
  7. }

Vous avez apporté cinq modifications au programme d'origine. Vous avez :

Écriture sur disque

Maintenant, n'appuyez pas sur la touche de fonction F2. Si vous le faites, ce programme sera enregistré sous BONJOUR.C (vous allez l'enregistrer sous un nom différent). Au lieu de cela, appuyez sur F10 pour accéder au menu principal. Appuyez sur F, puis sur W pour afficher la commande File/Write à commander. Le Turbo C vous demandera de saisir le nouveau nom de ce programme ; tapez sum.c et appuyez sur Enter. Votre deuxième programme est maintenant enregistré sur le disque sous le nom SUM.C. Appuyez sur F10 pour appeler à nouveau le menu principal.

Exécution de SUM.C

Appuyez sur R pour sélectionner la commande Run. Le Turbo C compilera votre programme. S'il y a des erreurs, retournez dans l'éditeur et assurez-vous que ce que vous avez tapé correspond exactement à ce qui est donné dans l'exemple. Une fois qu'il n'y a plus d'erreurs, le Turbo C établira un lien dans les routines de bibliothèque appropriées, puis exécutera votre programme. L'écran s'effacera et ce message apparaîtra en haut :

Entrez deux nombres :

Votre programme attend que vous saisissiez deux valeurs entières, séparées par des blancs et/ou des tabulations et/ou des retours chariot. Assurez-vous d'appuyer sur Enter après avoir saisi la deuxième valeur. Votre programme affiche maintenant la somme de ces deux valeurs, puis attend que vous appuyiez sur n'importe quelle touche avant de revenir à Turbo C. Toutes nos félicitations ! Vous avez maintenant écrit deux programmes Turbo C complètement différents en utilisant plusieurs des éléments de base de la programmation.

Les sept éléments de base de la programmation

Le but de la plupart des programmes est de résoudre un problème. Les programmes résolvent des problèmes en manipulant des informations ou des données. Vous avez à :

Vous pouvez organiser vos instructions de manière à :

Nous venons de décrire les sept éléments de base de la programmation : entrée, types de données, opérations, sortie, exécution conditionnelle, boucles et sous-programmes. Cette liste n'est pas exhaustive, mais elle décrit les éléments que les programmes ont généralement en commun.

La plupart des langages de programmation ont tout cela ; beaucoup, y compris C, ont également des fonctionnalités supplémentaires. Mais lorsque vous souhaitez apprendre rapidement une nouvelle langage de programmation, vous pouvez découvrir comment ce langage de programmation implémente ces sept éléments, puis construire à partir de là. Voici une brève description de chaque élément :

Éléments Description
Sortie Signifie écrire des informations sur l'écran, sur un disque ou sur un port d'entrée/sortie.
Types de données Sont des constantes, des variables et des structures contenant des nombres (entiers et réel, texte (caractères et chaînes) ou adresses (de variables et de structures).
Opérations Attribuer une valeur à une autre, combiner des valeurs (additionner, diviser,...) et comparer des valeurs (égales, différentes,...).
Saisir Signifie lire des valeurs à partir du clavier, d'un disque ou d'un port d'entrée/sortie.
Conditionnel L'exécution fait référence à l'exécution d'un ensemble d'instructions si une condition spécifiée est vraie (et à les ignorer si elle est fausse).
Boucles Exécuter un ensemble d'instructions un nombre fixe de fois ou tant qu'une condition est vraie.
Sous-programmes Sont des ensembles d'instructions nommés séparément pouvant être exécutés n'importe où dans le programme simplement par une référence au nom.

Nous allons maintenant voir comment utiliser ces éléments dans Turbo C.

Sortie

Cela peut sembler amusant de parler de sortie en premier, mais un programme ne produisant pas d'informations d'une manière ou d'une autre n'est pas très utile. Cette sortie prend généralement la forme d'informations écrites à l'écran (mots et images), sur un périphérique d'entreposage (disquette ou disque dur) ou sur un port d'entrée/sortie (port série, port d'imprimante).

La fonction printf

Vous avez déjà utilisé la fonction de sortie la plus courante en C : la routine printf. Le but de printf est d'écrire des informations à l'écran. Son format est à la fois simple et flexible :

printf(format-string, item, item>, ... );

La chaîne de caractères avec format

La chaîne de caractères de format est juste une chaîne de caractères commençant et se terminant par des guillemets ("comme ceci"); Le but de printf est d'écrire cette chaîne de caractères à l'écran. Cependant, printf remplace tout d'abord tous les éléments supplémentaires répertoriés dans la chaîne de caractères, en fonction des commandes de format trouvées dans la chaîne de caractères elle-même. Par exemple, votre dernier programme avait l'instruction printf suivante :

  1. printf("La somme de %d \n",sum);

Le %d dans la chaîne de caractères de format est une spécification de format. Toutes les spécifications de format commencent par un signe de pourcentage (%) et sont (généralement) suivis d'une seule lettre, indiquant le type de données et la manière dont les données doivent être formatées.

Vous devez avoir exactement un élément répertorié pour chaque spécification de format. Si l'élément est d'un type de données ne correspondant pas directement à la spécification de format, alors Turbo C tentera d'effectuer une conversion appropriée. Les éléments eux-mêmes peuvent être des variables, des constantes, des expressions, des appels de fonction. En bref, il peut s'agir de tout ce qui donne une valeur appropriée à la spécification de format correspondante.

Le %d utilisé dans cette spécification indique qu'il attend un entier. Voici quelques autres spécifications de format couramment utilisées :

Vous pouvez définir la largeur du champ en la plaçant entre le % et la lettre ; par exemple, un champ décimal de largeur 4 serait %4d. La valeur sera alors affichée justifiée à droite (avec des blancs au début), de sorte que la largeur totale du champ soit de 4. Si vous avez besoin d'afficher un signe de pourcentage, insérez simplement %%.

Le \n dans la chaîne n'est pas une spécification de format. Il est connu (pour des raisons historiques) comme une séquence d'échappement, et il représente un caractère spécial inséré dans la chaîne de caractères. Dans ce cas, le \n insère un caractère de saut de ligne, de sorte qu'après l'écriture de la chaîne de caractères, le curseur se déplace au début d'une nouvelle ligne.

Voici une liste des séquences d'échappement les plus couramment utilisées :

Et si vous avez besoin d'afficher une barre oblique inverse, insérez simplement \\.

Autres fonctions de sortie : puts et putchar

Il existe deux autres fonctions de sortie pouvant vous intéresser : puts et putchar. La fonction puts écrit une chaîne de caractères à l'écran suivie d'un caractère de saut de ligne.

Par exemple, vous pouvez réécrire BONJOUR.C comme :

  1. main() {
  2.  puts("Bonjour!")
  3. }

Notez que nous avons supprimé le \n à la fin de la chaîne de caractères; ce n'est pas nécessaire, puisque puts en ajoute un. D'autre part, la fonction putchar écrit un seul caractère à l'écran et n'ajoute pas de \n. L'instruction putchar(ch) équivaut à :

  1. printf("%c",ch);

Pourquoi voudriez-vous utiliser puts et/ou putchar au lieu de printf ? Une bonne raison est que la routine implémentant printf est plutôt volumineuse ; sauf si vous en avez besoin (pour une sortie numérique ou un formatage spécial), vous pouvez rendre votre programme à la fois plus petit et plus rapide en utilisant puts et putchar à la place. Par exemple, le fichier .EXE créé en compilant la version de BONJOUR.C utilisant puts est beaucoup plus petit que le fichier .EXE de la version utilisant printf.

Types de données

Lorsque vous écrivez un programme, vous travaillez avec un certain type d'informations, dont la plupart appartiennent à l'un des quatre types de base suivants : entiers, nombres à virgule flottante, texte et pointeurs :

Types Description
Entiers Sont les nombres avec lesquels vous avez appris à compter (1, 5, -21 et 752, par exemple).
Point flottant Les nombres ont des parties fractionnaires (3.14159) et des exposants (2.579x1024). Ceux-ci sont aussi parfois appelés nombres réels.
Texte Est composé de caractères (a, Z, !, 3) et de chaînes de caractères ("Ceci n'est qu'un test.").
Pointeurs Ne détenez pas d'informations ; au lieu de cela, chacun contient l'adresse d'un emplacement dans la mémoire de l'ordinateur contenant des informations.

Type flottant

Le C prend en charge ces quatre types de données de base sous diverses formes. Vous en avez déjà utilisé deux : les entiers (int) et les caractères (char). Vous allez maintenant modifier votre dernier programme pour utiliser un troisième type : la virgule flottante (float). Entrez dans l'éditeur Turbo C et modifiez votre programme pour qu'il ressemble à ceci :

  1. main () (
  2.  int a,b;
  3.  float ratio;
  4.  printf("Entrez deux nombres : ");
  5.  scanf("%d %d",&a,&b);
  6.  ratio = a / b;
  7.  printf("Le ratio est %f \n",ratio);
  8. }

Enregistrez-le sous RATIO.C en ouvrant les menus et en sélectionnant la commande File/Write to. Appuyez ensuite sur R pour compiler et exécuter le programme. Entrez deux valeurs (telles que 10 et 3) et notez le résultat (3,000000).

Vous vous attendiez probablement à une réponse de 3,333333 ; pourquoi la réponse était-elle juste 3 ? Comme a et b sont tous deux de type de données int, le résultat de a/b était donc de type de données int. Celui-ci a été converti en type de données float lorsque vous l'avez affecté à ratio, mais la conversion a eu lieu après la division, pas avant.

Revenez en arrière et changez le type de a et b en flottant ; changez également la chaîne de caractères de format "%d %d" dans scanf en "%f %f". Enregistrez le code (appuyez sur F2), puis compilez et exécutez. Le résultat est maintenant 3,333333, comme prévu.

Il existe également une grande version de type float, connue sous le nom de double. Comme vous l'avez peut-être deviné, les variables de type double sont deux fois plus grandes que les variables de type de données float. Cela signifie qu'ils ont des chiffres plus significatifs et une plus grande gamme d'exposants.

Les trois int

En plus du type de données int, le Turbo C prend en charge les short, int et les long, généralement abrégés en short et long. Les tailles actuelles de short, int et long dépendent de l'implémentation ; tout ce que C garantit, c'est qu'une variable de type short ne sera pas plus grande (c'est-à-dire qu'elle n'occupera pas plus d'octets) qu'une variable de type long. Dans le Turbo C, ces types occupent 16 bits (short), 16 bits (int) et 32 bits (long).

Non signé

Le Turbo C permet de déclarer certains types (char, short, int, long) non signés. Cela signifie qu'au lieu d'avoir des valeurs négatives, ces types ne contiennent que des valeurs non négatives (supérieures ou égales à zéro).

Les variables de ces types peuvent alors contenir des valeurs plus importantes que les types signés. Par exemple, dans Turbo C, une variable de type int peut contenir des valeurs de -32768 à 32767 ; un de type de données unsigned int peut contenir des valeurs de 0 à 65535. Les deux occupent exactement la même quantité d'espace (16 bits, dans ce cas) ; ils l'utilisent simplement différemment.

Définir une chaîne de caractères

Le Turbo C ne prend pas en charge un type de données de chaîne de caractères distinct, mais il fournit deux approches légèrement différentes pour définir les chaînes de caractères. L'une consiste à utiliser un tableau de caractères ; l'autre consiste à utiliser un pointeur de caractère.

Utilisation d'un tableau de caractères

Sélectionnez la commande Load dans le menu File et ramenez votre version modifiée de BONJOUR.C. Modifiez-la maintenant pour qu'elle apparaisse comme suit :

  1. main () {
  2.  char msg[30];
  3.  strcpy(msg,"Bonjour!");
  4.  puts(msg);
  5. }

Le [30] après msg indique au compilateur de réserver de l'espace pour un maximum de 29 caractères, c'est-à-dire un tableau de 29 variables char. (Le 30ème espace sera rempli par un caractère nul (\0) souvent désigné comme un terminateur nul.) La variable msg elle-même ne contient pas de valeur de caractère; il contient l'adresse (un emplacement en mémoire) de la première de ces 29 variables char. Lorsque le compilateur trouve l'instruction strcpy (msg, "Bonjour!"); ça fait deux choses :

Lorsque vous appelez puts(msg), vous transmettez la valeur dans msg, l'adresse de la première lettre vers laquelle il pointe, à puts. Met ensuite des vérifications pour voir si le caractère à cette adresse est le caractère nul. Si c'est le cas, alors puts est terminé ; sinon, puts affiche ce caractère, ajoute un (1) à l'adresse et vérifie à nouveau le caractère nul.

En raison de cette dépendance à un caractère nul, les chaînes de caractères en C sont connues comme étant terminées par un caractère nul : une séquence de caractères suivie du caractère nul. Cette approche supprime toute limite arbitraire sur la longueur des chaînes de caractères ; au lieu de cela, une chaîne de caractères peut avoir n'importe quelle longueur, tant qu'il y a suffisamment de mémoire pour la contenir.

Utilisation d'un pointeur de caractère

La deuxième méthode que vous pouvez utiliser pour définir des chaînes de caractères est un pointeur de caractère. Modifiez votre programme pour qu'il ressemble à ceci :

  1. main () {
  2.  char *msg;
  3.  msg = "Bonjour!";
  4.  puts(msg);    
  5. }

L'astérisque (*) devant msg indique au compilateur que msg est un pointeur sur un caractère ; en d'autres termes, msg peut contenir l'adresse d'un certain caractère. Cependant, le compilateur ne réserve aucun espace pour entreposer les caractères et n'initialise pas msg à une valeur particulière.

Lorsque le compilateur trouve l'instruction msg = "Bonjour!\n" ; ça fait deux choses :

La commande puts(msg) fonctionne comme avant, en affichant des caractères jusqu'à ce qu'elle rencontre le caractère nul.

Identificateurs

Jusqu'à présent, nous avons joyeusement donné des noms aux variables sans nous soucier des éventuelles restrictions. Parlons maintenant de ces restrictions.

Les noms que vous donnez aux constantes, aux types de données, aux variables et aux fonctions sont appelés identificateurs. Certains des identifiants utilisés jusqu'à présent incluent :

Identificateur Description
char, int, float Types de données prédéfinis
main Fonction principale du programme
name, a, b, sum, msg, ratio Variables définies par l'utilisateur
scanf, printf, puts Fonctions prédéclarées

Le Turbo C a quelques règles concernant les identificateurs ; voici un petit résumé :

Opérations

Une fois ces données entrées dans le programme (et dans vos variables), qu'allez-vous en faire ? Probablement le manipuler d'une manière ou d'une autre, en utilisant les opérateurs disponibles. Et C a beaucoup, beaucoup d'opérateurs.

Opérateur d'assignation

L'opération la plus simple est l'affectation, comme dans ratio == a / b ou ch == getch(). En Turbo C, l'affectation est un simple signe égal (=) ; la valeur à droite du signe égal est affectée à la variable de gauche. Vous pouvez empiler les affectations, telles que sum == a == b. Dans un cas comme celui-ci, l'ordre d'évaluation est de droite à gauche, de sorte que b serait affecté à a, qui à son tour serait affecté à la somme, donnant aux trois variables la même valeur (à savoir, la valeur d'origine de b).

Opérateurs unaires et binaires

Le Turbo C prend en charge l'ensemble habituel d'opérateurs arithmétiques binaires :

Le Turbo C prend en charge le moins unaire (a + (-b)), effectuant une négation arithmétique ; en tant qu'extension ANSI, le Turbo C prend également en charge le plus unaire (a + (+b)).

Opérateurs d'incrémentation (++) et de décrémentation (--)

Le Turbo C a également des opérateurs unaires et binaires spéciaux. Les opérateurs unaires les plus connus sont l'incrémentation (++) et la décrémentation (--). Ceux-ci vous permettent d'utiliser un seul opérateur ajoutant 1 ou soustrait 1 à n'importe quelle valeur ; l'addition ou la soustraction peut être effectuée au milieu d'une expression, et vous pouvez même décider si vous voulez qu'elle soit effectuée avant ou après l'évaluation de l'expression. Considérez les lignes de code suivantes :

  1. sum = a + b++;
  2. sum = a + ++b;

Le premier dit : «Ajoutez a et b ensemble, attribuez le résultat à la somme et incrémentez b de un.» La seconde dit, «Incrémentez b de un, additionnez a et b ensemble, et assignez le résultat à la somme.» Ce sont des opérateurs très puissants, mais vous devez vous assurer de bien les comprendre avant de les utiliser. Modifiez SUM.C comme suit, puis essayez de deviner quelle sera sa sortie avant de l'exécuter :

  1. main() {
  2.  int a,b,sum;
  3.  char *format;
  4.  format = "a = %d b = %d somme = %d \n";
  5.  a = b = 5;
  6.  sum = a + b; printf(format,a,b,sum);
  7.  sum = a++ + b; printf(format,a,b,sum);
  8.  sum = ++a + b; printf(format,a,b,sum);
  9.  sum = --a + b; printf(format,a,b,sum);
  10.  sum = a-- + b; printf(format,a,b,sum);
  11.  sum = a + b; printf(format,a,b,sum);
  12. }

Opérateurs au niveau du bit

Pour les opérations au niveau du bit, le Turbo C a les opérateurs suivants :

Ceux-ci vous permettent d'effectuer des opérations de très bas niveau sur les valeurs. Pour voir l'effet de ces opérateurs, saisissez et exécutez ce programme :

  1. main() {
  2.  int a,b,c;
  3.  char *formatl,*format2;
  4.  formatl = " %04X %5 %04X = %04X\n";
  5.  format2 = " %c%04X = %04X\n";
  6.  a = 0x0FF0; b = 0xFF00;
  7.  c = a << 4; printf(formatl,a,"<<",4,c);
  8.  c = a >> 4; printf(formatl,a,">>",4,c);
  9.  c = a & b; printf(formatl,a,"& ",b,c);
  10.  c = a | b; printf(formatl,a," | ",b,c);
  11.  c = a ^ b; printf(formatl,a,"^ ",b,c);
  12.  c = ~a; printf(format2,'~' ,a,c);
  13.  c = -a; printf(format2,'-' ,a,c);
  14. }

Encore une fois, voyez si vous pouvez deviner la sortie de ce programme avant de l'exécuter. Notez que des spécificateurs de largeur de champ ont été utilisés pour bien aligner la sortie ; le spécificateur %04X indique que nous voulons que la sortie utilise des zéros non significatifs, qu'elle ait une largeur de quatre chiffres et qu'elle soit en hexadécimal (base 16).

Opérateurs combinés

Le Turbo C vous permet d'utiliser un petit raccourci lors de l'écriture d'expressions contenant plusieurs opérateurs. Vous pouvez combiner l'opérateur d'affectation (=) avec les opérateurs discutés jusqu'à présent (unaire, binaire, incrément, décrément et bit à bit). À peu près n'importe quelle expression de la forme :

variable = variable operateur expression;

peut être remplacé par :

variable operator= expression;

Voici quelques exemples de telles expressions et comment elles peuvent être condensées :

Opérateurs d'adresse

Le Turbo C prend en charge deux opérateurs d'adresse spéciaux : l'opérateur d'adresse de (&) et l'opérateur d'indirection (*).

L'opérateur & renvoie l'adresse d'une variable donnée ; si sum est une variable de type de données int, alors &sum est l'adresse (emplacement mémoire) de cette variable. De même, si msg est un pointeur vers le type de données char, alors *msg est le caractère vers lequel pointe msg. Tapez le programme suivant et voyez ce que vous obtenez :

  1. main() {
  2.  int sum;
  3.  char *msg;
  4.  sum = 5 + 3;
  5.  msg = "Bonjour\n";
  6.  printf(" somme = %d &sum = %p\n",sum,&sum);
  7.  printf("*msg = %c msg = %p \n",*msg,msg);
  8. }

La première ligne affiche deux valeurs : la valeur de sum(8) et l'adresse de sum (attribuée par le compilateur). La deuxième ligne affiche également deux valeurs : le caractère vers lequel pointe msg (H) et la valeur de msg, étant l'adresse de ce caractère (également attribuée par le compilateur).

Entrée

Le Turbo C a plusieurs fonctions d'entrée ; certains prennent l'entrée d'un fichier ou d'un flux d'entrée, d'autres du clavier.

La fonction scanf

Pour une entrée interactive, vous utiliserez probablement scanf la plupart du temps. La fonction scanf est l'équivalent en entrée de printf ; sa syntaxe est la suivante :

scanf(chainedecaratere-de-format, adresse, adresse, ... )

La fonction scanf utilise plusieurs des mêmes formats %lettre que printf : %d pour les entiers, %f pour les valeurs à virgule flottante, %s pour les chaînes de caractères,... Cependant, il existe une différence importante avec scanf : les éléments suivant la chaîne de caractères de format doivent être des adresses et non des valeurs. Le programme SUM.C contient l'appel suivant :

  1. scanf("%d %d",&a,&b);

Cet appel indique au programme qu'il s'attend à ce que vous tapiez deux valeurs décimales (entières) séparées par un espace ; le premier sera affecté à a et le second à b. Notez qu'il utilise l'opérateur d'adresse de (&) pour transmettre les adresses de a et b à scanf.

Espace blanc

L'espace entre les deux commandes de format %d signifie en fait plus qu'un simple espace. Cela signifie que vous pouvez avoir n'importe quelle quantité d'espace entre les valeurs. Qu'est-ce qu'un espace blanc ? Toute combinaison d'espaces, de tabulations et de retours à la ligne. Les compilateurs et programmes Turbo C ignorent généralement les espaces blancs dans la plupart des cas.

Mais que se passe-t-il si vous vouliez séparer les nombres par une virgule au lieu d'un blanc ? Ensuite, vous pouvez modifier la ligne pour lire :

  1. scanf("%d,%d",&a,&b);

Cela vous permet d'entrer les valeurs avec une virgule entre elles.

Passer une adresse à scanf

Et si vous voulez saisir une chaîne de de caractères ? Tapez et exécutez le programme suivant :

  1. main() {
  2.  char name[30];
  3.  printf("Quel est votre nom : ");
  4.  scanf("%s",name);
  5.  printf("Bonjour, %s\n",name);
  6. }

Comme name est un tableau de caractères, la valeur de name est l'adresse du tableau lui-même. Pour cette raison, vous n'utilisez pas l'opérateur & devant le nom ; vous dites simplement scanf("%s", name).

Notez que nous avons utilisé l'approche par tableau (char name [30];) plutôt que l'approche par pointeur (char *name;). Pourquoi ? Parce que la déclaration de tableau réserve en fait de la mémoire pour contenir la chaîne de caractères, contrairement à la déclaration de pointeur. Si nous voulions utiliser char *name, nous devions alors allouer explicitement de la mémoire pour *name.

Utilisation de gets et getch pour Input

L'utilisation de scanf pour saisir des chaînes de caractères introduit cependant un autre problème. Exécutez à nouveau votre programme, mais cette fois tapez votre nom complet. Notez que le programme n'utilise que votre prénom dans sa réponse. Pourquoi ? Parce que, pour scanf, le blanc que vous avez tapé après votre prénom signalait la fin de la chaîne de caractères que vous entriez. Il y a deux solutions possibles à cela. Voici le premier :

  1. main() {
  2.  char first[20],middle[20],last[20];
  3.  printf("Quel est votre nom : ");
  4.  scanf("%s %s %s",first,middle,last);
  5.  printf("Bonjour, Dr. %s, ou devrais-je dire %s?\n",last,first);
  6. }

Ceci, bien sûr, suppose que vous ayez un deuxième prénom; dans cet exemple, scanf ne continuera pas tant que vous n'aurez pas tapé trois chaînes de caractères. Mais que se passe-t-il si vous voulez lire le nom entier comme une seule chaîne de caractères, des blancs et tout ? Voici la deuxième solution :

  1. main() {
  2.  char name[60];
  3.  printf("Quel est votre nom : ") ;
  4.  gets(name);
  5.  printf("Bonjour, %s\n",name);
  6. }

La fonction lit tout ce que vous tapez jusqu'à ce que vous appuyiez sur Enter. Il n'entrepose pas l'entrée dans la ligne ; mais il colle un caractère nul (\0) à la fin. Enfin, il y a la fonction getch. Il lit un seul caractère du clavier sans le renvoyer à l'écran (contrairement à scanf et gets). Notez qu'il ne prend pas ch comme paramètre ; à la place, getch est une fonction de type char, et sa valeur peut être assignée directement à ch.

Expressions conditionnelles

Il y a certains opérateurs dont nous n'avons pas encore parlé : les opérateurs relationnels et logiques. En outre, il existe certaines complexités concernant les expressions que nous avons enregistrées pour cette discussion sur les déclarations conditionnelles (vraies ou fausses).

Opérateurs relationnels

Les opérateurs relationnels vous permettent de comparer deux valeurs, produisant un résultat selon que la comparaison est vraie ou fausse. Si la comparaison est fausse, alors la valeur résultante est 0 ; si vrai, alors la valeur est 1. Voici une liste des opérateurs relationnels en Turbo C :

Pourquoi vous soucieriez-vous si quelque chose était vrai ou faux ? Chargez et exécutez le programme RATIO.C et voyez ce qui se passe lorsque vous entrez 0 pour la deuxième valeur. Votre programme affiche un message d'erreur Divide by zero et s'arrête.

Apportez maintenant les modifications suivantes à votre programme et exécutez-le à nouveau:

  1. main() {
  2.  float a,b,ratio;
  3.  printf("Entrez deux nombres : ");
  4.  scanf("%f %f",&a,&b);
  5.  if(b == 0.0) printf("Le ratio est non-definit\n");
  6.  else {
  7.   ratio = a / b;
  8.   printf("Le ratio est %f \n",ratio);    
  9.  }
  10. }

L'instruction sur les deux lignes après l'appel à scanf est connue sous le nom d'instruction if. Vous pouvez le lire comme suit : «Si la valeur de l'expression (b == 0,0) est vraie, appelez immédiatement printf. Si la valeur de l'expression est fausse, affectez a/b à ratio, puis appelez printf.» Maintenant, si vous entrez 0 comme deuxième valeur, votre programme affiche le message :

Le ratio est non-definit

attend que vous appuyiez sur une touche, puis revient à Turbo C. Si la deuxième valeur est différente de zéro, le programme calcule et affiche le rapport, puis attend que vous appuyiez sur une touche, tout au long de la magie de l'instruction if.

Opérateurs logiques

Il existe également trois opérateurs logiques : AND (&&), OR (||) et NOT (!). Ceux-ci ne doivent pas être confondus avec les opérateurs au niveau du bit (&, |, ~) décrits précédemment. Ces opérateurs logiques fonctionnent avec des valeurs logiques (vrai et faux), vous permettant de combiner des expressions relationnelles.

En quoi diffèrent-ils des opérateurs binaires correspondants ?

En savoir plus sur les expressions

Avant de passer aux boucles, nous avons quelques commentaires supplémentaires sur les expressions. Des choses comme (b == 0.0) et (a <= q* r) sont assez simples. Cependant, le Turbo C vous permet de rendre les choses plus compliquées que cela. Beaucoup plus compliqué. Nous ne vous montrerons pas à quel point c'est compliqué, mais nous vous donnerons quelques conseils.

Déclarations d'affectation

Toute instruction d'affectation entre parenthèses est une expression ayant la même valeur que celle étant affectée. Par exemple, l'expression (somme = 5+3) a la valeur 8, de sorte que l'expression ((somme = 5+3) <= 10) donnerait toujours une valeur vraie (puisque 8 <= 10).

Plus exotique est cet exemple :

  1. if ((ch=getch()) == 'q') puts("Quitter, hein ?\n");
  2.                     else puts("Bon mouvement; nous allons essayer de nouveau\n");

Pouvez-vous comprendre ce que cela fait ? Lorsque votre programme atteint l'expression ( (ch=getch ()) == 'q'), il s'arrête jusqu'à ce que vous appuyiez sur un caractère, assigne ce caractère à ch, puis compare ce même caractère à la lettre q. Si le caractère sur lequel vous avez appuyé est égal à q, alors le message "Quitter, hein ?" est affiché sur l'écran; sinon, l'autre message ("Bon mouvement ...") est affiché.

Opérateur à virgule

Vous pouvez utiliser l'opérateur virgule (,) pour placer plusieurs expressions entre parenthèses. Les expressions sont évaluées de gauche à droite et l'expression entière prend la valeur de la dernière évaluée. Par exemple, si oldch et ch sont tous les deux de type de données char, alors l'expression :

  1. (oldch = ch, ch = getch())

assigne ch à oldch, obtient un caractère du clavier et l'assigne à ch, puis assume la valeur (assignée) de ch.

Par exemple :

  1. ch = 'a';
  2. if((oldch = ch, ch = 'b') == 'a') puts("aye");
  3.                              else puts("abeille");

L'instruction if

Regardez à nouveau l'instruction if dans les exemples précédents. L'instruction if prend le format générique suivant :

if(valeur) instruction1;
      else instruction2;

valeur est une expression se résolvant en (ou peut être convertie en) une valeur entière. Si la valeur est différente de zéro (vrai), alors instruction1 est exécutée ; sinon, instruction2 est exécutée. Nous devons expliquer deux points importants concernant les instructions if-else en général. Tout d'abord, la partie else instruction2 est facultative ; en d'autres termes, il s'agit d'une instruction if valide :

if(valeur) instruction1;

Dans ce cas, instruction1 est exécutée si et seulement si la valeur est différente de zéro. Si la valeur est zéro, alors instruction1 est ignorée et le programme continue. Deuxièmement, que se passe-t-il si vous souhaitez exécuter plusieurs instructions si une expression particulière est vraie (ou fausse) ? Réponse : Utilisez une instruction composée. Une instruction composée consiste en :

L'exemple de ratio utilise une seule instruction pour la clause if :

  1. if(b == 0.0) printf("Le ratio est non-définit\n");

et une instruction composée pour la clause else :

  1. else {
  2.  ratio = a / b;
  3.  printf("Le ratio est %f \n",ratio);
  4. }

Vous remarquerez peut-être aussi que le corps de votre programme (la fonction main) est simplement une instruction composée.

Boucles

Tout comme il existe des instructions (ou des groupes d'instructions) que vous souhaitez exécuter de manière conditionnelle, il existe d'autres instructions que vous pouvez exécuter de manière répétée. Ce type de construction est connu sous le nom de boucle.

Il existe trois types de boucles de base (bien que deux ne soient que des cas particuliers de l'autre) : la boucle while, la boucle for et la boucle do...while. Nous les aborderons dans cet ordre.

La boucle while

La boucle while est la boucle la plus générale et peut être utilisée pour remplacer les deux autres ; en d'autres termes, une boucle while est tout ce dont vous avez besoin, et les autres sont juste là pour votre commodité. Chargez BONJOUR.C et modifiez-le comme suit :

  1. #include <stdio.h>
  2.  
  3. main () (
  4.  int len;
  5.  len = 0;
  6.  puts("Tapez une phrase, puis appuyez sur <Enter>");
  7.  while(getchar() != '\n') len++;
  8.  printf("\nVotre phrase faisait %d caractères de long\n",len);    
  9. }

Ce programme vous permet de taper une phrase, en comptant le nombre de frappes, jusqu'à ce que vous appuyiez sur Enter (\n). Il vous indique ensuite le nombre de caractères (sans compter Enter) que vous avez saisis. Le format de l'instruction while est :

while (expression) instruction

expression se résout en une valeur nulle ou différente de zéro, et instruction est une instruction simple ou composée.

La boucle while évalue l'expression. Si c'est vrai, alors l'instruction est exécutée et l'expression est à nouveau évaluée. Si l'instruction n'est pas vraie, la boucle while est terminée et le programme continue.

Jetez un oeil à un autre exemple de boucle while, basé sur BONJOUR.C :

  1. main() {
  2.  char *msg;
  3.  int indx;
  4.  msg = "Bonjour";
  5.  indx = 1;
  6.  while (indx <= 10) {
  7.   printf("heure #%2d: %s\n",indx,msg);
  8.   indx++;
  9.  }
  10. }

Lorsque vous compilez et exécutez ce programme, il affiche les lignes suivantes :

heure #1: Bonjour
heure #2: Bonjour
heure #3: Bonjour

et ainsi de suite, jusqu'à :

time #10: Bonjour
.

L'instruction printf a été exécutée exactement dix fois, l'index allant de 1 à 10 au cours de ces dix exécutions. Si vous y réfléchissez, vous verrez peut-être un moyen d'écrire cette boucle un peu plus serrée :

  1. indx = 0;
  2. while (indx++ < 10) printf ("heure #%2d: %s\n", indx,msg);

Étudiez cette deuxième boucle while jusqu'à ce que vous compreniez pourquoi elle fonctionne exactement de la même manière que la première version. Ensuite, continuez et découvrez la boucle for.

La boucle for

La boucle for est celle que l'on trouve dans la plupart des principaux langages de programmation, y compris C. Cependant, la version Turbo C de la boucle for est très flexible et très puissante, comme vous le verrez.

L'idée de base est que vous exécutez un ensemble d'instructions un nombre fixe de fois tandis qu'une variable (appelée variable d'index) parcourt une intervalle de valeurs.

Par exemple, modifiez le programme précédent pour lire comme suit :

  1. main() {
  2.  char *msg;
  3.  int indx;
  4.  msg = "Bonjour";
  5.  for (indx = 1; indx <= 10; indx++) printf("heure #%2d: %s\n",indx,msg);
  6. }

Comme vous pouvez le voir lorsque vous l'exécutez, cela fait la même chose que les deux boucles while déjà montrées et, en fait, est précisément équivalente à la première. Voici le format générique de l'instruction de boucle for :

for(exp1; exp2; exp3) instruction

Comme pour while, l'instruction for exécute une seule instruction, mais cette instruction peut être une instruction composée ({ ... }). Notez ce qui est à l'intérieur des parenthèses après le mot pour ; il y a trois sections séparées par des points-virgules.

exp1;
while (exp2) {
   instruction;
   exp3;
}

Vous pouvez omettre une ou toutes les expressions, bien que les points-virgules doivent rester. Si vous omettez exp2, il est supposé avoir une valeur de 1 (vrai), donc la boucle ne se termine jamais (c'est ce qu'on appelle une boucle infinie).

D'autre part, vous pouvez utiliser l'opérateur virgule pour insérer plusieurs expressions pour chaque expression. Par exemple, essayez ces modifications sur BONJOUR.C :

  1. main() {
  2.  char *msg;
  3.  int up, down;
  4.  msg = "Bonjour";
  5.  for (up = I, down = 9; up <= 10; up++, down--) printf("%s: %2d bas, %2d est allé\n",msg,up,down);    
  6. }

Notez que les première et dernière expressions de cette boucle for ont chacune deux expressions, initialisant et modifiant les variables vers le haut et vers le bas. Vous pouvez rendre ces expressions arbitrairement complexes. (Peut-être avez-vous entendu les légendes des hackers C ayant entassé la plupart de leurs programmes dans les trois expressions d'une instruction for, ne laissant que quelques instructions à exécuter par la boucle.)

La boucle do...while

La dernière boucle est la boucle do...while. Modifiez RATIO.C comme suit :

  1. main() {
  2.  float a,b,ratio;
  3.  char Ch;
  4.  do {
  5.   printf("Entrer deux nombres : ");
  6.   scanf("%f %f",&a,&b);
  7.   if(b == 0.0) printf ("Le ratio est non-définit\n");
  8.   else {
  9.    ratio = a / b;
  10.    printf("Le ratio est %f \n",ratio);
  11.   }
  12.   printf("Presse 'q' pour quitter, n'importe quel autres touches pour continuer");
  13.   } while ((ch = getch ()) ! = ' q');
  14. }

Ce programme calcule un ratio, puis vous demande d'appuyer sur une touche. Si vous appuyez sur q, l'expression en bas est fausse et la boucle se termine. Si vous appuyez sur une touche autre que q, l'expression est vraie et la boucle se répète.

Voici le format générique pour la boucle do...while :

do instruction while (exp);

La principale différence entre la boucle while et la boucle do...while est que les instructions de la boucle do...while s'exécutent toujours au moins une fois. Ceci est similaire à la boucle Repeat...Until en langage de programmation Pascal, avec une différence majeure : la boucle répéter s'exécute jusqu'à ce que sa condition soit vraie ; do...while s'exécute tant que sa condition est vraie.

Les fonctions

Vous avez appris à exécuter du code de manière conditionnelle et itérative. Maintenant, que se passe-t-il si vous souhaitez exécuter le même ensemble d'instructions sur différents ensembles de données ou à différents endroits de votre programme ? Réponse : Vous placez ces instructions dans un sous-programme, que vous appelez ensuite si nécessaire.

En Turbo C, tous les sous-programmes sont appelés fonctions. En théorie, chaque fonction renvoie une valeur. En pratique, les valeurs renvoyées par de nombreuses fonctions sont ignorées et les définitions plus récentes de Turbo C (y compris le projet de norme ANSI C et Turbo C) vous permettent de déclarer des fonctions de type de données void, ce qui signifie qu'elles ne renvoient aucune valeur. Jamais.

En Turbo C, vous pouvez à la fois déclarer et définir une fonction. Lorsque vous déclarez une fonction, vous en informez le reste de votre programme afin que d'autres fonctions (y compris main) puissent l'appeler. Lorsque vous définissez une fonction, vous donnez le code réel de la fonction elle-même. Par exemple, considérez cette réécriture de RATIO.C :

  1. /* Déclarations de fonction */
  2. void get_parms(float *p1, float *p2);
  3. float get_ratio(float dividend, float divisor);
  4. void put_ratio(float quotient);
  5.  
  6. const float INFINITY = 3.4E+38;
  7. /* Fonction principal : Point de départ pour le programme */
  8. main() {
  9.  float a,b,ratio;
  10.  do {
  11.   get_parms(&a,&b);                   /* Demande les paramètres */
  12.   ratio = get_ratio(a,b);             /* Calcul le ratio */
  13.   put_ratio(ratio);                   /* Affiche la réponse à a sortie */
  14.   printf("Presse q pour quitter, n'importe quel autre touche pour continuer.");
  15.  } while(getch() != 'q');
  16. }
  17. /* Fin de la fonction principale */
  18.  
  19. /* Définitions de fonctions */    
  20. void get_parms(float *p1,float *p2) {
  21.  printf("\nEntrer deux nombres: ");
  22.  scanf("%f %f",p1,p2);
  23. }
  24.  
  25. float get_ratio(float dividend, float divisor) {
  26.  if(divisor == 0.0) return(INFINITY);
  27.                else return (dividend / divisor);
  28. }
  29.  
  30. void put_ratio(float ratio) {
  31.  if (ratio == INFINITY) printf("Le ratio est non-définit\n");
  32.                    else printf("Le ratio est %f\n",ratio);
  33. }

Décomposer le programme

Les trois premières lignes du programme sont les déclarations de fonction ; leur but est de déclarer le type de la fonction ainsi que le type et le nombre des paramètres à des fins de contrôle d'erreur.

La ligne suivante définit une constante à virgule flottante appelée INFINITY (c'est une convention C de nommer les constantes en majuscules). Cette constante a une valeur positive très élevée - à peu près la plus élevée que vous puissiez avoir avec le type de données float - et est utilisée pour signaler une division par zéro. Notez que puisqu'il est déclaré ici, il est "visible" dans toutes les fonctions (y compris main).

Vient ensuite la fonction main, étant le corps principal de votre programme. Chaque programme Turbo C a une fonction appelée main ; lorsque votre programme commence à s'exécuter, main est appelé et tout se déroule à partir de là. Une fois l'exécution de main terminée, votre programme est terminé et vous revenez à Turbo C (ou, si vous avez exécuté à partir d'un prompt DOS, à DOS).

La fonction main peut être placée n'importe où dans le programme ; c'est souvent la première ou la dernière fonction, après tout prototype ou autre déclaration globale. Cela facilite la recherche et aide à documenter la fonction de l'ensemble du programme.

Après main viennent les définitions réelles des trois fonctions déclarées dans les prototypes : get_parms, get_ratio et put_ratio. Nous allons maintenant examiner chacune de ces définitions.

La fonction get_parms

La fonction get_parms ne renvoie pas de valeur d'un type donné, nous l'avons donc déclarée de type de données void. Cependant, son but est de lire deux valeurs et de les stocker quelque part. Où ? Nous devons passer deux paramètres à get_parms ; ces paramètres sont les adresses où les valeurs doivent être entreposées. Regardez bien : les deux paramètres ne sont pas de type de données float mais sont des pointeurs vers le type de données float. En d'autres termes, elles sont supposées être des adresses de variables flottantes.

C'est exactement ce que nous transmettons : lorsque nous appelons get_parms dans main, les paramètres sont &a,&b au lieu de simplement a,b. Notez également que lorsque scanf est appelé à l'intérieur de get_parms, il n'y a pas d'opérateur d'adresse de devant p1 et p2. Pourquoi ? Parce que p1 et p2 sont déjà des adresses ; ce sont les adresses de a et b.

La fonction get_ratio

La fonction get_ratio renvoie une valeur (de type de données float) calculée à partir des deux valeurs flottantes lui étant passées (dividende et diviseur). La valeur renvoyée dépend du fait que le diviseur est 0 ou non. Si c'est le cas, get_ratio renvoie INFINITY. Si le diviseur n'est pas 0, get_ratio renvoie le rapport actuel. Notez le format de l'instruction de retour.

La fonction put_ratio

La fonction put_ratio ne renvoie pas de valeur, elle est donc de type void. Il n'a qu'un seul paramètre - ratio - étant utilisé pour déterminer ce qu'il faut afficher à l'écran. Si le rapport est égal à l'INFINI, alors il est considéré comme indéfini ; sinon, le rapport est affiché.

Déclarations globales

Les constantes, les types de données et les variables déclarés en dehors de toute fonction (y compris main) sont considérés comme globaux à partir de ce moment. Cela signifie qu'ils peuvent être utilisés par n'importe quelle fonction dans l'ensemble du programme après leur déclaration. Si vous deviez déplacer la déclaration de INFINITY à la fin du programme, vous obtiendriez deux erreurs de compilation, une dans get_ratio et une dans put_ratio, pour l'utilisation d'un identificateur non déclaré.

Déclarations de fonction

Vous pouvez utiliser deux styles différents pour déclarer des fonctions : le style "classique" et le style "moderne". Le style classique, que l'on retrouve dans de nombreux textes et programmes en Turbo C, prend cette forme :

  1. type funcname();

Cela spécifie le nom de la fonction (funcname) et le type de valeur de données qu'elle renvoie (type). Il ne donne aucune information sur les paramètres, donc aucune vérification d'erreur ou coercition de type ne peut être effectuée. Si vous réécriviez les déclarations de fonction dans RATIO.C en utilisant ce style, elles ressembleraient à ceci :

  1. void get_parms();
  2. float get_ratio();
  3. void put_ratio();

Le style moderne utilise une construction des extensions ANSI connue sous le nom de prototype de fonction. Cette déclaration ajoute des informations de paramètre :

  1. type funcname(pinfo,pinfo,...);

pinfo prend l'un des formats suivants :

type
type pname
...

En d'autres termes, pour chaque paramètre formel, vous pouvez spécifier uniquement le type de données, ou vous pouvez également lui donner un nom. Si la fonction prend un nombre variable de paramètres, vous pouvez utiliser les points de suspension (...) pour le dernier paramètre.

C'est l'approche préférée, car elle permet au compilateur de vérifier les nombres et les types des paramètres dans les appels réels à la fonction. Cette approche permet également au compilateur d'effectuer des conversions appropriées lorsque cela est possible. Les déclarations de fonction trouvées dans la version précédente de RATIO.C sont des prototypes de fonction.

Définitions des fonctions

Comme pour les déclarations de fonctions, il existe deux styles de définitions de fonctions : classique et moderne. Le format classique d'une définition de fonction est le suivant :

type funcname(pnames)
parm definitions;
{
   local declarations;
   statements;
}

Le format moderne déplace les définitions des paramètres entre parenthèses après funcname :

type funcname(pinfo,pinfo,...)

Dans cet exemple, cependant, le terme pinfo représente toutes les informations sur un paramètre donné ; ses modificateurs de type et son nom d'identificateur. Ainsi, la première ligne de la définition de la fonction ressemble exactement au prototype de fonction correspondant, à une exception près : il n'y a pas de point-virgule (;) après la définition, alors qu'un prototype de fonction se termine toujours par un point-virgule. Par exemple, la fonction get_parms dans le style classique ressemble à ceci :

  1. void get_parms(p1, p2)
  2. float *p1; float *p2;
  3. { ... }

et dans le style moderne ça ressemble à ça :

  1. void get_parms (float * p1, float *p2)
  2. { ... }    

Notez que toutes les déclarations (constantes, types de données, variables) effectuées dans une fonction donnée (y compris main) sont visibles (c'est-à-dire qu'elles peuvent être utilisées et référencées) uniquement dans cette fonction. Notez également que Turbo C n'autorise pas les fonctions imbriquées ; vous ne pouvez pas déclarer une fonction à l'intérieur d'une autre.

Les fonctions peuvent également être placées dans n'importe quel ordre dans le programme et sont considérées comme globales dans tout le programme, y compris dans les fonctions déclarées avant celles étant utilisées. Soyez prudent lorsque vous utilisez une fonction avant qu'elle ne soit définie ou déclarée : lorsque le compilateur rencontre une fonction qu'il n'a jamais vue auparavant, il suppose que la fonction renvoie un int. Si vous la définissez plus tard pour qu'elle renvoie autre chose, disons un char*, vous obtiendrez une erreur.

Commentaires ou remarques

Parfois, vous souhaitez insérer des notes dans votre programme pour vous rappeler (ou informer quelqu'un d'autre) ce que signifient certaines variables, ce que font certaines fonctions ou instructions,.. Ces notes sont appelées commentaires ou remarques. En Turbo C, comme la plupart des autres langages de programmation, vous permet d'insérer des commentaires dans votre programme.

Pour commencer un commentaire, vous insérez la séquence de caractères barre oblique-étoile (/*). À partir de là, le compilateur ignorera tout jusqu'à ce qu'il voie une autre séquence */. Les commentaires peuvent même s'étendre sur plusieurs lignes, comme ceci :

  1. /* C'est un long 
  2. commentaire s'étendant
  3. sur plusieurs lignes.  */

Regardez dans la version étendue de RATIO.C pour des exemples supplémentaires de commentaires.



Dernière mise à jour : Mardi, le 2 mars 2021