Vous êtes sur la page 1sur 38

Programmation Classique en C.

doc ______________________________________________________________________________

DI GALLO Frdric

Programmation Classique en langage C


Cours du Cycle dApprofondissement

CNAM ANGOULEME 2000-2001 ___________________________________________________________________


DI GALLO Frdric Page 1 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

PROGRAMMATION

CLASSIQUE : LANGAGE C

___________________________________________________________________
DI GALLO Frdric Page 2 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

PROGRAMMATION CLASSIQUE EN C
I. LES VARIABLES DE TYPE SIMPLE ...........................................................................4 II. LES VARIABLES DE TYPE STRUCTURE ..................................................................6 III. INTERET DES TYPES SIMPLES & STRUCTURES.....................................................8 IV. LES INSTRUCTIONS DU LANGAGE ........................................................................10 4.1) L'instruction d'affectation..........................................................................................10 4.2) Les instructions dentre-sortie .................................................................................15 4.3) Les instructions de choix ...........................................................................................17 4.4) Les instructions itratives ..........................................................................................20 V. LES FONCTIONS ET LES BIBLIOTHEQUES ...............................................................23 5.1) Utilisation et cration de fonctions ...........................................................................23 5.2) La fonction main() .....................................................................................................27 VI. ANNEXES .........................................................................................................................29 6.1) Calcul des primtres et surface d'un rectangle.........................................................29 6.2) Calcul d'une note arrondie au point.......................................................................29 6.3) Vrification de la majorit..........................................................................................30 6.4) Affichage de l'anne scolaire en cours .......................................................................31 6.5) Somme de deux horaires.............................................................................................32 6.6) Oprations mathmatiques simples ............................................................................33 6.7) PGCD par la division EUCLIDIENNE ......................................................................34 6.8) Connatre le nombre de chiffre d'un entier ................................................................35 6.9) Test des fonctions PGCD et arrondi...........................................................................36

___________________________________________________________________
DI GALLO Frdric Page 3 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

INFORMATIQUE CNAM ANGOULEME 2000-2001

PROGRAMMATION CLASSIQUE EN C
I. LES VARIABLES DE TYPE SIMPLE

On rappelle quen programmation classique, pour mmoriser une valeur en mmoire centrale, il est ncessaire dintroduire une variable. Celle-ci est dfinie au moyen de deux lments : son nom encore appel identificateur - qui permet daccder la valeur quelle contient et de la manipuler dans lalgorithme ou dans le programme, son type qui prcise la nature de la valeur quelle peut accueillir. Par exemple en C, la dclaration suivante dfinit deux variables destines accueillir respectivement un entier et un caractre. int I ; char C ; Remarque : le langage C distingue les lettres minuscules des lettres majuscules. Les identificateurs i et I dsignent donc deux variables diffrentes. Le type dune variable induit plus prcisment la reprsentation de la valeur en mmoire centrale et donc lespace - en terme doctets - monopolis par cette valeur. Ainsi, le type int permet daccueillir un entier cod en arithmtique signe sur deux octets. Le type char utilise quant lui le code ASCII (un octet) pour reprsenter un caractre. La dclaration dune variable peut donc tre assimile la rservation en mmoire centrale dun emplacement dont la taille dpend de son type. On peut reprsenter de la manire suivante les consquences de la dclaration des deux variables I et C. I 2 octets C 1 octet

Pour la mmorisation des nombres, le langage C propose diffrents types dont la taille dpend de limplmentation en machine. Le tableau ci-dessous prsente les caractristiques des types numriques proposs par TURBO C. Nom du type Nature de la valeur Nbre doctets int Entier sign 2 short Entier sign 2 long Entier sign 4 float Rel 4 double Rel 8 Domaine -32 768 ; 32 767 -32 768 ; 32 767 -2 147 483 648 ; 2 147 483 647 3.4 10 38 ; 3.4 10 38 1.7 10 308 ; 1.7 10 308

Il est important de noter quen C la dclaration dune variable nentrane pas son initialisation et le compilateur signalera une erreur si le programmeur la rfrence sans lavoir initialise. Linitialisation dune variable peut se faire au moment de sa dclaration de la manire suivante : NomDuType NomVariable=Valeur;

___________________________________________________________________
DI GALLO Frdric Page 4 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________ Les valeurs entires sont de type int , mais on peut leur affecter un type long en suffixant leur nom dun l ou dun L . Par exemple la valeur 32L dsigne une valeur entire de type long . De mme les valeurs relles sont par dfaut de type double , mais on peut leur affecter un type float en suffixant leur nom dun f ou dun F . Lors d'une initialisation, il est important de veiller la compatibilit du type de la valeur et de la variable. Le langage C ralise des conversions de type avec ventuellement perte dinformation. Par exemple la dclaration int I=78 934 est accepte par le compilateur C mais entrane laffectation de la valeur 13 398 dans la variable I. La dclaration float tva=5.5 est aussi accepte alors que la valeur 5.5 est de type double alors que la variable destine accueillir la variable est de type float . Il serait plus juste dcrire float tva=5.5f .

Application 1: On considre le programme C suivant :


void main() { int I=32767 ; long J= 48L ; char C=A,NL=\n ; } Remarque : la constante '\n' dsigne le caractre non visualisable 'LF'. Son affichage provoque un changement de ligne. a) Indiquer pour chaque variable la reprsentation en binaire de la valeur quelle contient. I: 7F FFh J: 00 00 00 30h C: 41h NL: 0Ah b) On enrichit le programme de linstruction qui consiste incrmenter le contenu de la variable I. Donner en binaire et en dcimal la nouvelle valeur contenue dans I. I: 7F FF + 1 = -32768 (a revient en arrire puisque le C boucle). c) Expliquer, pourquoi le langage C permet de comparer deux caractres et autorise de telles critures : C=A+1 ; Pour le langage C, 'A' correspond au code 65h, il fait 65+1 = 66h or 'B'=66h. Si l'on teste C<'E', la rponse sera oui car 'A'=65h est infrieur 'E'=69h.

Application 2: Codage du sexe d'une personne.


Pour coder le sexe d'une personne, certains organismes utilisent les valeurs 1 et 2. Proposer, en C, la dclaration d'une variable destine mmoriser ce code. On choisit un caractre pour limiter la taille un octet.

___________________________________________________________________
DI GALLO Frdric Page 5 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

II. LES VARIABLES DE TYPE STRUCTURE


Une variable de type structur permet de mmoriser plusieurs valeurs, qui ont un lien entre elles, en les regroupant sous un nom unique. Par exemple pour mmoriser les N notes dun lve il est plus judicieux dutiliser la variable de type structur Notes qui regroupe toutes les notes, plutt que dutiliser N variables de type simple. Les deux grands types structurs sont : - le tableau ( 1 ou 2 dimensions) qui regroupe des valeurs de mme type, - lenregistrement qui est compos de valeurs ayant des types diffrents.

Le tableau denregistrements est un driv des deux types prcdents puisquil sagit
dun tableau 1 dimension dans lequel chaque composant est un enregistrement. Comme pour les variables de type simple, toute dclaration dune variable de type structur entrane la rservation en mmoire centrale dun emplacement dont la structure et la taille dpend du type. Le tableau ci-dessous prsente des exemples de variables de types structurs. Tableau 1 dimension T de 5 entiers 0 1 2 3 4 int T[5]; Tableau 2 dimensions TD dentiers (4 lignes et 3 colonnes) 0 0 1 2 3 int TD[4][3]; struct horaire { int heure; int minute; }; struct horaire H; 1 2 Enregistrement H compos de deux champs : heure, minute heure minute

Laccs aux valeurs contenues dans une variable de type structur est ralis en mentionnant le nom de la variable suivi dune information qui identifie la valeur dans la variable. Par exemple, pour accder au ime composant du tableau T 1 dimension on utilise la rfrence T[i+1] car le premier composant porte le numro 0. Pour accder au composant heure de lenregistrement H, il faut utiliser la notation : H.heure. Exemple de tableau d'enregistrement: Famille Nom Prnom Age 0 C B 18 1 B O 17 2 C B 23 Struct personne Famille[30] Famille[2].age Famille[0] Remarque : pour mmoriser une chane de caractres lune des possibilits en C est de dclarer un tableau 1 dimension de caractres. Par exemple la dclaration char Mess[25] permet de stocker un message dau plus 25 caractres dans la variable Mess.

___________________________________________________________________
DI GALLO Frdric Page 6 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

Application 1: On considre le programme C suivant :


void main() { struct LigneCommande { int NumeroProduit ; int NumeroCommande ; int Qte ; }; struct LigneCommande T[100] ; } Calculer en octets lespace monopolis par le tableau T. LigneCommande = 6 octets car NumeroProduit, NumeroCommande, Qte sont des entiers (2 octets). Ce qui donne pour T[100]: 600 octets.

Application 2: On souhaite utiliser le tableau Decomp:


1 dimension pour mmoriser la dcomposition binaire dun entier (type : int ) saisi au clavier. Par exemple la dcomposition de la valeur 23 sera mmorise ainsi : 0 1 2 3 4 5 6 7 1 0 1 1 1

Remarque : le bit de plus fort poids est plac dans le composant 0 du tableau Decomp. Combien de composants devra-t-on dclarer pour le tableau Decomp afin quil soit en mesure de mmoriser la dcomposition binaire de tout entier saisi au clavier ? Un entier correspond 2 octets donc 16 bits. Decomp devra donc tre en mesure de contenir 16 composants. On le dclare par int Decomp[16].

___________________________________________________________________
DI GALLO Frdric Page 7 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

III. INTERET des TYPES SIMPLES & STRUCTURES


Dans de nombreuses informatisations, lune des tapes fondamentales du dveloppement consiste passer dune reprsentation externe de linformation une reprsentation interne en mmoire centrale ou sur support stockage permanent. Cette reprsentation interne doit permettre dune part de retrouver la reprsentation externe de linformation, moyennant lapplication dun processus dtermin, et dautre part de mettre en uvre, le plus facilement possible, tous les traitements que lon souhaite raliser sur linformation. Elle doit en outre optimiser lespace mmoire. Les reprsentations internes en mmoire centrale sont bases sur tous les types simples ou structurs vus prcdemment. Ainsi pour implmenter en mmoire centrale le polynme : 5x4 + 3x + 2, on pourra envisager les deux solutions illustres et commentes ci-dessous : On introduit la variable P de type chane de caractres suivante : 5x4 +3x+2 On introduit le tableau denregistrements P suivant : Coeff 5 3 2 Degr 4 1 0

Cette implantation ne se prte pas une exploitation facile car lextraction des monmes constituant le polynme impose la mise en uvre dun traitement complexe sur les chanes de caractres.

Cette reprsentation interne est satisfaisante et permet de dvelopper sans trop de difficults toutes les oprations sur un polynme.

___________________________________________________________________
DI GALLO Frdric Page 8 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

Application 1: Proposer une reprsentation interne :


en mmoire centrale pour implanter un arbre binaire. Un arbre binaire est un arbre dont chaque sommet admet au plus deux fils. Exemple darbre binaire : A B F I E J

La reprsentation propose devra permettre une exploitation simple de larborescence et dans un mme temps une optimisation de la mmoire. Lexploitation concerne les oprations lmentaires que lon peut effectuer sur un arbre cest--dire : - la consultation du pre, des fils et des frres dun sommet, - lajout et la suppression dun sommet. Info A B E F I J Avec racine: 0 Fils gauche Fils droit 1 2 3 0 4 5 0 0 0 0 0 0

Application 2: Proposer une reprsentation interne :


pour implanter un jeu de 32 cartes. Cette reprsentation devra permettre de mettre en uvre nimporte quel jeu de cartes avec ses propres rgles. Une carte est reprsente par sa valeur et sa couleur: valeur couleur 0 1 Carreau 1 7 Pique 2 dame Trfle ... 31 . .

___________________________________________________________________
DI GALLO Frdric Page 9 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

IV. LES INSTRUCTIONS DU LANGAGE


Les instructions du langage permettent de dvelopper des traitements sur des variables de tous les types vus prcdemment. En C chaque instruction se termine par un point virgule. Ces instructions peuvent tre classes en 4 grandes catgories : - linstruction daffectation, - les instructions dentre-sortie, - lalternative, - litrative

4.1) L'instruction d'affectation


Elle permet d'affecter dans une variable de type simple ou dans un composant d'une variable de type structur le rsultat d'une expression. Le type de ce rsultat doit tre compatible avec le type de la variable. Syntaxe : Variable=Expression; Lexpression peut porter sur des nombres ou des chanes de caractres. Dans le cas dune expression de type arithmtique, celle-ci peut faire intervenir 3 types de composants : - des rfrences des variables numriques de type simple ou des composants de variables de type structur, - des constantes, encore appeles littraux, - des oprateurs.

Les oprateurs arithmtiques:


Le tableau ci-dessous rcapitule les oprateurs arithmtiques autoriss en C : Symbole + * / % ++ -Opration addition soustraction multiplication division Modulo (reste de la division euclidienne) incrmentation dcrmentation

Les oprateurs +, -, *, / peuvent tre combins avec laffectation. Ainsi lexpression i += j est quivalente i = i + j . Les deux derniers oprateurs sont unaires. Leur rle est dincrmenter ou de dcrmenter le contenu de la variable. Ainsi, les expressions ++i ou i++ ajoute une unit la variable i. Lorsquils sont intgrs lexpression dune affectation il est important de noter quils modifient le contenu de la variable laquelle ils sont attachs. Dans une telle situation laffectation ne modifie plus seulement le contenu de la variable place gauche du signe =. Selon la position de loprateur par rapport la variable (avant ou aprs) lvaluation de lexpression composant le membre droit de laffectation prendra la valeur de la variable avant quelle soit modifie ou aprs.

___________________________________________________________________
DI GALLO Frdric Page 10 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________ Dans lexemple suivant les deux affectations modifient le contenu de la variable i qui prend la valeur 3. La premire affectation renvoie la valeur 2 j alors que la seconde renvoie la valeur 3. void main() { int i =2; int j; j=i++ ; j=++i ; } En plus des oprateurs cits dans le tableau ci-dessus, il existe loprateur ternaire qui permet linclusion dune expression conditionnelle dans le calcul dune expression. Sa syntaxe a la valeur suivante : (expression logique) ? ExpressionSiVrai : ExpressionSiFaux. Par exemple, lexpression (i>0) ?i*2 :i+2, renvoie le produit de i par 2 si i est strictement positif et le rsultat de lajout de 2 i si i est ngatif ou nul.

Les oprateurs de comparaison:


Dans lexpression logique, on peut mentionner les oprateurs de comparaison classiques : <, >, <=, >=, ==(gal), != (diffrent) ainsi que les oprateurs boolens : &&(et) et ||(ou).

Application 1: Remise de 20% pour plus de 3 articles achets :


La socit X applique une remise de 20% si le nombre darticles achets est strictement suprieur 3. Ecrire lexpression qui permet de valoriser la variable MontantAPayer partir des deux variables supposes renseignes : TotalAchats et NbProduits qui reprsentent respectivement le montant total des achats et le nombre darticles achets. void main() { int NbProduits; float MontantAPayer, TotalAchat;
Saisie de NbProduits et TotalAchat

MontantAPayer = (NbProduits>3)?TotalAchats-(TotalAchats*0.20):TotalAchats; }

___________________________________________________________________
DI GALLO Frdric Page 11 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

Auto-valuation 1:

___________________________________________________________________
DI GALLO Frdric Page 12 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________ Lvaluation de toute expression repose dune part sur les rgles de priorit entre les oprateurs en labsence dun parenthsage et dautre part sur les types des oprandes qui constituent lexpression. Pour ce dernier point, il est utile de savoir que lordinateur ne sait calculer une expression arithmtique de la forme oprande1 oprateur oprande2 que lorsque les deux oprandes sont du mme type. Lorsque ce nest pas le cas, lordinateur transforme le type de lun des oprandes pour que les deux membres deviennent du mme type. La conversion applique suit une hirarchie destine ne pas perdre linformation. Ainsi lorsque lon a une variable de type float et une variable de type int il y aura conversion automatique de la seconde variable en float . Le rsultat obtenu est toujours du mme type que celui des deux oprandes. Avec un tel principe le rsultat de lexpression 5/2 est gal 2 et non 2.5 car 5 et 2 sont des valeurs de type int . En revanche, lexpression 5/2f fournit 2.5 comme rsultat car lordinateur convertit en float les deux oprandes.

Application 1: On considre le programme C suivant :


void main() { int i=5,j=2,k ; float w,x,y,z ; w=i/2+1; x=i/2f+1; y=++i/2 +1/2f; z=i++/j + 1/2; } Fournir le contenu des variables w, x, y et z lissue des diffrentes affectations executes. w=3; x=3.5; y=3+0.5=3.5; z=3; i=7;

L'oprateur de transtypage:
Loprateur de cast encore appel oprateur de transtypage - permet de modifier le type dune variable dans une expression arithmtique. Cet oprateur qui a une priorit suprieure aux oprateurs arithmtiques usuels scrit en entourant par des parenthses le type vers lequel on veut transformer une expression. Le programme ci-dessous illustre le principe de cet oprateur. void main() { int i=5,j=2 float x ; x=i/j; x=(float)i/j; x=(float)(i/j); }

/* le rsultat est 2 car i et j sont des entiers ; le rsultat est donc un entier */ /* le rsultat est 2.5 car loprateur (float) (prioritaire par rapport la division) */ /* a transform le type de la variable i en float ; le rsultat est donc un float */ /* le rsultat est 2 car la division est value et donne un entier qui est ensuite */ /* transform en rel */

___________________________________________________________________
DI GALLO Frdric Page 13 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________ I + J Oprande 1 Oprateur Oprande 2 Type T1 Type T2 oui T <- T1 T1 = T2 non
Conversion de type Soit T1 vers T2 Soit T2 vers T1

Le rsultat est de type T Sens de la conversion int --------- > float ------>double

Application 1: On considre les expressions arithmtiques suivantes :


1.5+(float)i/j; 1.5+(float)(i+1)/(float)j +5/i; 1+(float)(i/2f)+(float)(i/j); a) En supposant que i et j sont deux variables entires qui contiennent respectivement les valeurs 5 et 2, fournir le rsultat retourn par chaque expression. 1.5+(float)i/j; 1.5+(float)(i+1)/(float)j +5/i; 1+(float)(i/2f)+(float)(i/j); 4 1.5+3+1= 5.5 1+2.5+2= 5.5

b) Indiquer les cast qui sont inutiles. 1.5+(float)i/j; 1.5+(float)(i+1)/(float)j +5/i; 1+(float)(i/2f)+(float)(i/j);

___________________________________________________________________
DI GALLO Frdric Page 14 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

4.2) Les instructions dentre-sortie


Linstruction scanf():
Elle permet dacqurir en mmoire centrale une valeur. Cette valeur sera place dans une variable de type simple ou dans un composant dune variable de type structur. Le format prcise le type de valeur qui doit tre saisi et affect dans la variable. Le tableau ci-dessous prsente les formats associs aux diffrents types tudis prcdemment. Syntaxe : scanf( format ,&Variable) Format %d %D %f %c

Type int ou short long float ou double char

Par exemple, linstruction scanf ( %d ,&I) permet dacqurir un entier et de le stocker dans la variable I de type int . Lexpression &Variable correspond ladresse de la variable. Cest le contenu de cette adresse qui sera valorise par la fonction scanf ().

Linstruction printf():
Elle permet dafficher lcran un message pouvant intgrer des expressions faisant rfrence des variables de type simple ou des composants de variables de type structur. Le format prcise le type de la valeur contenue dans la variable cite. Il peut prendre de nombreuses valeurs mais on se limitera aux mmes valeurs que pour linstruction scanf(). Syntaxe : printf ( Message format , variable ou expression)

Par exemple, linstruction printf ( le double de %d est %d\n, I, I*2) affiche le message le double de 5 est 10 si le contenu de la variable I est 5. Le caractre \n provoque un retour la ligne aprs laffichage du message.

___________________________________________________________________
DI GALLO Frdric Page 15 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

Application 1: Ecrire le programme C :


qui calcule et affiche la surface ainsi que le primtre dun rectangle dont on saisit la longueur et la largeur. On suppose que ces valeurs sont des entiers. #include <stdio.h> void main() { float surface, perimetre, longueur, largeur; clrscr(); printf ("Saisir la longueur: "); scanf ("%f",&longueur); printf ("\nSaisir la largeur: "); scanf ("%f",&largeur); perimetre=2*(longueur+largeur); surface=longueur*largeur; printf("\n\nle primtre est %f et la surface est %f",perimetre,surface); getch(); }

Application 2: Ecrire le programme C :


qui calcule la note arrondie au point suprieur dune note saisie au clavier. #include <stdio.h> void main() { float note,notea,i; clrscr(); printf ("Saisir la note: "); scanf ("%f",&note); i=note-(int)note; notea=(i==0)?note:(i>0.5)?(int)note+1:(int)note+0.5; printf ("\nLa note arrondie est %f",notea); getch(); }

___________________________________________________________________
DI GALLO Frdric Page 16 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

4.3) Les instructions de choix


L'instruction conditionnelle IF:
La syntaxe gnrale de lalternative a la forme suivante : if (expression boolenne) { bloc1 dinstructions /* si le rsultat de l'expression boolenne est VRAI les instructions */ } /*du bloc1 sont excutes, sinon les instructions du bloc 2 sont excutes*/ else { bloc2 dinstructions } Remarques : Chaque instruction lintrieur dun bloc se termine par un point virgule. La partie else est facultative. Dans le cas o le bloc est form dune seule instruction il nest pas utile de mentionner les accolades. Les principaux oprateurs relationnels que lon peut mentionner dans lexpression boolenne ont t cits lors de ltude de loprateur ternaire.

L'instruction de slection SWITCH:


Lorsque lon doit tester le contenu dune variable avec de nombreuses valeurs et dclencher des traitements particuliers pour chacune de ces valeurs, il est recommand dutiliser linstruction switch plutt quune imbrication dinstructions if else . La syntaxe de cette instruction a la forme suivante : switch (NomVariable) {case Valeur1 : {bloc dinstructions} case Valeur2 : {bloc dinstructions} default : {bloc dinstructions} } Linstruction switch, compare la valeur contenue dans la variable avec chacune des valeurs cites aprs le mot cl case . Ds quelle trouve la correspondance elle excute le bloc dinstructions associ. La dernire instruction associe un bloc doit tre break afin de passer linstruction qui suit le switch. Dans le cas o aucune correspondance nest trouve, linstruction switch excute soit le bloc dinstructions associe la clause dfault si celle-ci est mentionne, soit passe linstruction qui suit linstruction switch .

___________________________________________________________________
DI GALLO Frdric Page 17 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

Application 1: Ecrire le programme de lexemple dexcution suivant :


(les valeurs saisies sont soulignes) : Oprande 1 : 124 Oprateur (+, *, -): + Oprande2 : 35 Rsultat : 159 On suppose que les oprandes saisis sont des entiers de type int .

#include <stdio.h>

/* Appel la bibliothque stdio */

void main() { int a,b,result,B=0,encore=0; char operateur; do { clrscr(); /* efface l'cran */ printf ("\noprande n1 : "); /* Affiche l'interrogation */ scanf ("%d",&a); /* rcupre l'oprande date saisie par l'utilisateur */ printf ("\noprateur (+,*,-) : "); scanf ("%s",&operateur); printf ("\noprande n2 : "); /*on demande l'oprande n2 */ scanf ("%d",&b); switch (operateur) { case '+': { result=a+b; break; } case '-': { result=a-b; break; } case '*': { result=a*b; break; } default : { printf ("\n\nl'oprateur saisie n'est pas correct"); B=1;} } if (B==0) printf ("\n\nRsultat : %d",result); getch(); /* attente de validation */ printf ("\n\n Voulez vous encore jouer (entrez 1 pour Oui)?"); scanf ("%d",&encore); /* on rcupre la rponse */ } while (encore==1); /* si la rponse est 1, on relance la boucle */ } /* fin */

___________________________________________________________________
DI GALLO Frdric Page 18 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

Application 2: Complter le programme C suivant :


afin quil affiche la somme de deux horaires saisis en dbut de traitement. Par exemple l'opration 23:30 + 2:30 donnera : 02:00. void main() { struct horaire { int heure; int minute; }; struct horaire H1,H2,H3; int encore=0;

/* Dclaration d'un type date */ /* 1ere case : entier jour */ /* 2ieme case : entier mois */ /* D du type date contiendra la date saisie */

do { clrscr(); /* efface l'cran */ printf ("\nhoraire n1 : "); /* Affiche l'interrogation */ scanf ("%d:%d",&H1.heure,&H1.minute); /* rcupre la date saisie par l'utilisateur */ printf ("\n\nhoraire n2 : "); /*on crit l'anne scolaire en cours */ scanf ("%d:%d",&H2.heure,&H2.minute); H3.heure=H1.heure+H2.heure; H3.minute=H1.minute+H2.minute; if (H3.minute>=60) { H3.minute-=60; H3.heure++; } if (H3.heure>=24) H3.heure-=24; printf ("\n\nSomme des horaires : %d:%d",H3.heure,H3.minute); getch(); /* attente de validation */ printf ("\n\n Voulez vous encore jouer (entrez 1 pour Oui)?"); scanf ("%d",&encore); /* rcupre la rponse */ } while (encore==1); /* si la rponse est 1, on relance la boucle */ } /* fin */

___________________________________________________________________
DI GALLO Frdric Page 19 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

4.4) Les instructions itratives


On rappelle quen algorithmique, il existe plusieurs instructions pour mettre en uvre un traitement itratif. Le choix entre ces diffrentes instructions est bas sur le nombre ditrations comme le montre le schma ci-dessous : Le nombre ditrations est-il connu ? OUI NON

Instruction Pour .. FinPour

Le nombre ditrations peut-il tre nul ? OUI NON

Instruction TqueFinTQ Instruction algorithmique TantQue Condition Faire Bloc d'instructions FinTQ Rpter Bloc d'instructions Jusqu Condition Pour Compteur Valeur initiale Valeur finale Bloc d'instructions FinPour

Instruction Rpter Jusqu

Traduction en langage C while (Condition) { Bloc dinstructions } do { Bloc dinstructions } while (!(Condition)) For (Compteur=Valeur initiale ;Compteur <=Valeur finale ; Compteur ++) { Bloc dinstructions }

Remarques : Si le bloc dinstructions est limit une seule, on peut se dispenser des accolades. La condition spcifie dans linstruction do while est la ngation de la condition exprime dans le Rpter jusqu . Lexcution de linstruction : for(expression1 ;expression2 ;expression3) {bloc dinstructions} est quivalente la squence dinstructions suivante : Evaluer expression1 While (Expression2) { bloc dinstructions Evaluer expression3 }

___________________________________________________________________
DI GALLO Frdric Page 20 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

Application 1: Traduire en langage C lalgorithme suivant :


qui est destin calcul le plus grand commun diviseur de deux nombres a et b saisis au clavier (mthode dEuclide). On suppose que a est suprieur b. Variables a, b, r : Entier Dbut Afficher ( Valeur de a : ) Entrer a Afficher ( Valeur de b : ) Entrer b r a mod b TantQue r <> 0 Faire a b b r r a mod b FTQ Afficher Le PGCD est : , b Fin Remarque : l'expression a mod b renvoie le reste de la division euclidienne de a par b. #include <stdio.h> void main() { int a,b,r=1; clrscr(); printf ("\n\nValeur de a : "); scanf ("%d",&a); printf ("\nValeur de b : "); scanf ("%d",&b); r=a%b; while (r!=0) { a=b; b=r; r=a%b; } printf ("\n\nLe PGCD est : %d",b); getch(); }

___________________________________________________________________
DI GALLO Frdric Page 21 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

Application 2: Ecrire le programme C qui affiche le nombre de chiffres qui compose un entier positif saisi au clavier :
#include <stdio.h> void main() { int i=0,test=0; struct stat { int valeur; int effectif; }; struct stat tstat[100]; clrscr(); do { printf ("\n\nEntrer la valeur de la case %d du tableau : ",i); scanf ("%d",&tstat.valeur[i]); printf ("\n\nEntrer l'effectif de la case %d du tableau : ",i); scanf ("%d",&tstat.effectif[i] while (entier>9) { i++; entier/=10; } printf ("\n\nNombre de chiffres : %ld",i); getch(); i=1; printf ("\n\nVoulez vous continuer (Oui=1) :"); scanf ("%ld",&test); } while (test==1);

Application 3: on considre le tableau d'enregistrements Tstat ci-dessous :


et destin contenir une srie statistique simple. Struct Stat { int Valeur; int Effectif; }; struct stat Tstat [100]; Ecrire un programme C qui enchane les diffrents traitements suivants : - valorisation du tableau Tstat par la saisie d'une liste de valeurs ; la fin de la saisie sera marque par la valeur 999, - affichage, pour chaque valeur diffrente saisie, de son effectif, - affichage de la valeur qui admet le plus grand effectif. On suppose que cette valeur est unique.

___________________________________________________________________
DI GALLO Frdric Page 22 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

Application 4: On considre le tableau deux dimensions TD d'entiers :


(8 lignes, 8 colonnes) dfini ci-dessous. Ecrire un programme C qui demande l'utilisateur : - la valeur d'un entier, - le composant du tableau qu'il veut renseigner avec la valeur prcdemment saisie en respectant la codification suivante : T pour l'intgralit du tableau, E pour une cellule du tableau ; dans ce cas l'utilisateur doit identifier le numro de ligne et le numro de colonne de la cellule, L pour une ligne du tableau ; dans ce cas l'utilisateur doit identifier le numro de ligne, C pour une colonne du tableau ; dans ce cas l'utilisateur doit identifier le numro de colonne, D pour la diagonale : coin haut gauche, coin bas droit. Un exemple d'excution du programme est fourni ci-dessous (les valeurs saisies sont soulignes) : Valeur ? 5 Composant ? L N de ligne ? 5 Pour simplifier l'algorithme, on ne devra pas envisager de contrle sur les numros de ligne et/ou de colonne saisis.

V.

Les FONCTIONS et les BIBLIOTHEQUES


5.1) Utilisation et cration de fonctions

Dans ce paragraphe, seuls les modules admettant: - 0 n paramtres dentre - 0 ou 1 paramtre de sortie seront traits et seront dsigns par le terme de fonction. Cette terminologie diffre en algorithmique. Dans ce domaine, on appelle, en effet, fonction les modules qui admettent 1 et 1 seul paramtre de sortie, et procdure les autres modules Une fonction est un outil destine faciliter le dveloppement dapplications. Ainsi, le langage C fournit dans des bibliothques, des fonctions pour rpondre aux besoins de diverses applications. Par exemple, la bibliothque math.h regroupe diffrentes fonctions trigonomtriques et logarithmiques. Pour pouvoir utiliser les fonctions dune bibliothque il faut spcifier la clause #include <NomDeLaBibliothque> en dbut de programme. Le programme C ci-dessous utilise la fonction sqrt de la bibliothque math.h pour calculer les solutions de lquation du second degr ax2+bx+c=0. #include <math.h> void main()

___________________________________________________________________
DI GALLO Frdric Page 23 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________ {float a,b,c,delta ; delta =b*b-4*a*c ; if (delta < 0) printf ( pas de solution relle\n ) ; else if (delta == 0) printf ( la solution double est : %f\n ,-b/(2*a)) ; else { printf ( la premire solution est : %f\n ,(-b-sqrt(delta))/(2*a)) ; printf ( la seconde solution est : %f \n, (-b+sqrt(delta)/(2*a)) ; } } Le programmeur peut aussi crer ses propres fonctions et ensuite les intgrer dans une bibliothque afin de les mettre la disposition dautres programmeurs. En C, la cration dune fonction respecte la syntaxe suivante : TypeRes NomFonction (Liste des paramtres d'entre) { Dclaration des variables locales Liste des instructions } Remarques : Chaque paramtre dentre est dcrit par son type suivi de son nom ; les paramtres dans la liste sont spars par une virgule. Dans le cas o la fonction ne renvoie aucun rsultat, cest le mot cl void qui est spcifi avant le nom de la fonction. Dans le cas o la fonction renvoie un rsultat, cest linstruction return (Expression) qui permet de renvoyer au programme appelant le rsultat souhait. Les exemples ci-dessous prsentent deux fonctions : lune charge de renvoyer le primtre dun rectangle partir des deux paramtres dentre reprsentant la longueur et la largeur, lautre charge dafficher ce mme primtre. int Perimetre(int Largeur, int longueur) { return (2*(Largeur+Longueur)) ; } void AffichePerimetre (int Largeur, int Longueur) { printf ( le primtre est : %d ,2*(Largeur+Longueur)) }

___________________________________________________________________
DI GALLO Frdric Page 24 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________ Dans le programme appelant, il va de soi que lappel de la fonction diffre totalement selon si la fonction renvoie 0 ou 1 rsultat. Ainsi une fonction de type void doit sutiliser comme une instruction, alors quune fonction qui renvoie un rsultat doit tre intgre une instruction algorithmique. Ce propos est illustr par les appels des deux fonctions prsentes ci-dessus. void main() { printf( le primtre dun rectangle de largeur 2 et de longueur 4 est : %d , Perimetre(2,4)) ; AffichePerimetre(2, 4) ; }

Application 1: Ecrire la fonction Cqui calcule et renvoie le PGCD :


de deux entiers positifs a et b. On suppose que a est suprieur b. int pgcd (int a, int b) { int r; r=a%b; while (r!=0) {a=b; b=r; r=a%b;} return (b); }

Application 2: fonction qui calcule larrondi au point suprieur dune valeur :


float arrondi (float note) { int notea,i; i = note - ( int ) note; notea = (i = = 0 ) ? note : ( i > 0.5 ) ? ( int ) note + 1 : ( int ) note + 0.5; return (notea); }

___________________________________________________________________
DI GALLO Frdric Page 25 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

Application 3: La bibliothque date.h :


propose diffrentes fonctions permettant de manipuler des dates. Parmi celles-ci on trouve les deux fonctions suivantes : int numerojour(struct date d) fonction qui renvoie le numro du jour dans lanne associ la date d struct date converdate(int q) fonction qui renvoie la date associe au quantime q int nombrejours (int a) fonction qui renvoie le nombre de jours de l'anne a date est un type dfini ci-dessous : struct date { int jour ; int mois ; int annee ; }; a) Ecrire le programme C qui affiche la date du lendemain dune date saisie au clavier b) Transformer ce programme en une fonction qui calcule la date du lendemain

___________________________________________________________________
DI GALLO Frdric Page 26 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

5.2) La fonction main()


Tout programme crit en langage C doit comporter une fonction main() qui est le point dentre de lapplication. Cela signifie que lors du lancement de lapplication depuis lenvironnement du systme dexploitation (DOS, ou UNIX), lordinateur excutera les instructions contenues dans la fonction main() . Par exemple, la saisie sous DOS de la commande pgcd dclenchera lexcution du contenu de la fonction main() associe ce programme. Pour permettre lutilisateur de mentionner des paramtres au niveau de la commande de lancement de son application on doit mentionner dans len-tte de la fonction main() les paramtres argc et argv . Le paramtre argc est un entier donnant le nombre darguments de la ligne de commande passs main() . Le paramtre argc est un tableau de chanes de caractres contenant toutes les valeurs des arguments passs main() . Le programme ci-dessous prsente la fonction main() associ au calcul du PGCD de deux nombres a et b avec a et b non plus saisis lors de lexcution mais valoriss dans la commande de lancement. On suppose que la bibliothque arith.h contient la fonction PGCD. #include <arith.h> void main(int argc, char * argv[]) {if (argc != 3) printf ( erreur sur le nombre darguments ) ; else printf ( la valeur du PGCD de %d et %d est : %d , a, b, PGCD(atoi(argv[1]),atoi(argv[2]))) ; } Remarques : Le nom de la commande est considr comme un argument. , La fonction atoi transforme une chane de caractres reprsentant un entier en un entier. Pour calculer le PGCD de 24 et 16, lutilisateur devra saisir, depuis lenvironnement du systme dexploitation la commande : pgcd 24 16 Lors du lancement de lapplication, les arguments sont spars par des espaces. Dans le cas o un argument intgre lui-mme des espaces, il est ncessaire de lencadrer par des guillemets. La fonction main() peut retourner un rsultat qui est un code destin raliser un compte-rendu sur lexcution du programme. Si dans le programme, linstruction exit(numro) est rfrence, cest le numro fourni en argument de linstruction exit qui est retourn. Pour exploiter le rsultat retourn par la fonction main, il faut spcifier lentte de la fonction main() de la manire suivante : int main(.)

___________________________________________________________________
DI GALLO Frdric Page 27 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________ Travaux pratiques 1. On souhaite construire la bibliothque fraction.h destine raliser les oprations suivantes sur les fractions : - initialiser une fraction partir de la donne dun numrateur et dun dnominateur - afficher une fraction sous la forme : numrateur/dnominateur - ajouter deux fractions - multiplier deux fractions - diviser deux fractions - calculer linverse dune fraction - mettre sous forme irrductible une fraction a) Proposer une reprsentation interne pour implanter en mmoire centrale une fraction. b) Dfinir en C, pour chacune des oprations cites, linterface de la fonction charge de la raliser. c) Ecrire en langage C le contenu de chacune des fonctions. Les tester sur machine.

2. On souhaite construire la bibliothque periode.h destine raliser les oprations suivantes sur des priodes horaires caractrises par un horaire dbut (exprim en heure minute) infrieur un horaire fin (exprim en heure minute). - initialiser une priode partir de la donne dun horaire dbut et dun horaire fin. On suppose que lhoraire dbut est infrieur lhoraire fin - afficher une priode sous la forme [hh1 :mm1 ;hh2 :mm2] - calculer lintersection entre deux priodes ; dans le cas o la priode rsultat est vide, la priode [00 :00 ;00 :00] sera renvoye. - Calculer le nombre de minutes associe une priode a) Proposer une reprsentation interne pour implanter en mmoire centrale une priode ainsi dfinie. b) Dfinir en C, pour chacune des oprations cites, linterface de la fonction charge de la raliser. c) Ecrire en C le contenu de chacune des fonctions. Les tester sur machine.

___________________________________________________________________
DI GALLO Frdric Page 28 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

VI. ANNEXES
6.1) Calcul des primtres et surface d'un rectangle
#include <stdio.h> void main() { float surface, perimetre, longueur, largeur; clrscr(); printf ("Saisir la longueur: "); scanf ("%f",&longueur); printf ("\nSaisir la largeur: "); scanf ("%f",&largeur); perimetre=2*(longueur+largeur); surface=longueur*largeur; printf("\n\nle primtre est %f et la surface est %f",perimetre,surface); getch(); }

6.2) Calcul d'une note arrondie au point


#include <stdio.h> void main() { float note,notea,i; clrscr(); printf ("Saisir la note: "); scanf ("%f",&note); i=note-(int)note; notea=(i==0)?note:(i>0.5)?(int)note+1:(int)note+0.5; printf ("\nLa note arrondie est %f",notea); getch(); }

___________________________________________________________________
DI GALLO Frdric Page 29 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

6.3) Vrification de la majorit


#include <stdio.h> void main() { struct date { int jour; int mois; int annee; }; struct date N,J; int an,mois,jour,test=0; clrscr(); printf ("Date de naissance : "); scanf ("%d/%d/%d",&N.jour,&N.mois,&N.annee); printf ("\nDate du jour : "); scanf ("%d/%d/%d",&J.jour,&J.mois,&J.annee); an=J.annee-N.annee; if (an>18) test=1; else { if (an<18) test=0; else { mois=J.mois-N.mois; if (mois>0) test=1; else { if (mois<0) test=0; else { jour=J.jour-N.jour; if (jour>=0) { test=1; if (jour==0) printf ("\n\nBON ANNIVERSAIRE!!!"); } else test=0; } } } } if (test==0) printf ("\n\nVous tes mineur"); else printf ("\n\nVous tes majeur"); getch(); }

___________________________________________________________________
DI GALLO Frdric Page 30 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

6.4) Affichage de l'anne scolaire en cours


#include <stdio.h> void main() { struct date /* Dclaration d'un type date */ { int jour; /* 1ere case : entier jour */ int mois; /* 2ieme case : entier mois */ int annee; /* 3ieme case : entier annee */ }; struct date D; /* D du type date contiendra la date saisie */ int an=0,encore=0; /* entier an contiendra l'anne ajustee */ /* boolen encore pour boucle de relance du prog */ do { /* lance la boucle de relance du prog */ clrscr(); /* efface l'cran */ printf ("\nDate du jour ? "); /* Affiche l'interrogation */ scanf ("%d/%d/%d",&D.jour,&D.mois,&D.annee); /* rcup. date saisie par l'utilisateur*/ if (D.mois>8) { /* teste si le mois est postrieur aout */ an=D.annee+1; /* si oui, an recoit annee + 1 */ printf ("\n\nAnne scolaire : %d-%d",D.annee,an); /*crit anne scol en cours*/ } else { an=D.annee-1; /* sinon, an recoit annee - 1 */ printf ("\n\nAnne scolaire : %d-%d",an,D.annee); /* on ecrit l'anne en cours */ } getch(); /* attente de validation */ printf ("\n\n Voulez vous encore jouer (entrez 1 pour Oui)?"); /* demande si l'on veut relancer le programme */ scanf ("%d",&encore); /* rcupre la rponse */ } while (encore==1); /* si la rponse est 1, on relance la boucle */ } /* fin */

___________________________________________________________________
DI GALLO Frdric Page 31 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

6.5) Somme de deux horaires


#include <stdio.h> void main() { struct horaire { int heure; int minute; }; struct horaire H1,H2,H3; int encore=0; /* Appel la bibliothque stdio */

/* Dclaration d'un type date */ /* 1ere case : entier jour */ /* 2ieme case : entier mois */ /* D du type date contiendra la date saisie */

do { clrscr(); /* efface l'cran */ printf ("\nhoraire n1 : "); /* Affiche l'interrogation */ scanf ("%d:%d",&H1.heure,&H1.minute); /* rcupre la date saisie par l'utilisateur */ printf ("\n\nhoraire n2 : "); /*on crit l'anne scolaire en cours */ scanf ("%d:%d",&H2.heure,&H2.minute); H3.heure=H1.heure+H2.heure; H3.minute=H1.minute+H2.minute; if (H3.minute>=60) { H3.minute-=60; H3.heure++; } if (H3.heure>=24) H3.heure-=24; printf ("\n\nSomme des horaires : %d:%d",H3.heure,H3.minute); getch(); /* attente de validation */ printf ("\n\n Voulez vous encore jouer (entrez 1 pour Oui)?"); scanf ("%d",&encore); /* rcupre la rponse */ } while (encore==1); /* si la rponse est 1, on relance la boucle */ } /* fin */

___________________________________________________________________
DI GALLO Frdric Page 32 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

6.6) Oprations mathmatiques simples


#include <stdio.h> /* Appel la bibliothque stdio */

void main() { int a,b,result,B=0,encore=0; char operateur; do { clrscr(); /* efface l'cran */ printf ("\noprande n1 : "); /* Affiche l'interrogation */ scanf ("%d",&a); /* rcupre l'oprande date saisie par l'utilisateur */ printf ("\noprateur (+,*,-) : "); scanf ("%s",&operateur); printf ("\noprande n2 : "); /*on demande l'oprande n2 */ scanf ("%d",&b); switch (operateur) { case '+': { result=a+b; break; } case '-': { result=a-b; break; } case '*': { result=a*b; break; } default : { printf ("\n\nl'oprateur saisie n'est pas correct"); B=1;} } if (B==0) printf ("\n\nRsultat : %d",result); getch(); /* attente de validation */ printf ("\n\n Voulez vous encore jouer (entrez 1 pour Oui)?"); scanf ("%d",&encore); /* on rcupre la rponse */ } while (encore==1); /* si la rponse est 1, on relance la boucle */ } /* fin */

___________________________________________________________________
DI GALLO Frdric Page 33 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

6.7) PGCD par la division EUCLIDIENNE

#include <stdio.h> void main() { int a,b,r=1; clrscr(); printf ("\n\nValeur de a : "); scanf ("%d",&a); printf ("\nValeur de b : "); scanf ("%d",&b); r=a%b; while (r!=0) { a=b; b=r; r=a%b; } printf ("\n\nLe PGCD est : %d",b); getch(); }

___________________________________________________________________
DI GALLO Frdric Page 34 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

6.8) Connatre le nombre de chiffre d'un entier


#include <stdio.h> void main() { int i=0,test=0; struct stat { int valeur; int effectif; }; struct stat tstat[100]; clrscr(); do { printf ("\n\nEntrer la valeur de la case %d du tableau : ",i); scanf ("%d",&tstat.valeur[i]); printf ("\n\nEntrer l'effectif de la case %d du tableau : ",i); scanf ("%d",&tstat.effectif[i] while (entier>9) { i++; entier/=10; } printf ("\n\nNombre de chiffres : %ld",i); getch(); i=1; printf ("\n\nVoulez vous continuer (Oui=1) :"); scanf ("%ld",&test); } while (test==1);

___________________________________________________________________
DI GALLO Frdric Page 35 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

6.9) Test des fonctions PGCD et arrondi


#include <stdio.h> float arrondi(float note) { int notea,i; i=note-(int)note; notea=(i==0)?note:(i>0.5)?(int)note+1:(int)note+0.5; return (notea); } int pgcd (int a, int b) { int r; r=a%b; while (r!=0) {a=b; b=r; r=a%b;} return (b); } void main() { int var1,var2,test=1; float var3; clrscr(); do { clrscr(); printf ("\nSaisir les deux nombres : "); scanf ("%d %d",&var1,&var2); printf ("\nle PGCD est %d",pgcd(var1,var2)); getch(); printf ("\nVoulez vous continuer (Non=0)? "); scanf ("%d",&test); } while (test!=0); test=1; do { clrscr(); printf ("\Saisir la note : "); scanf ("%f",&var3); printf ("\La note arrondie est %f",arrondi(var3)); getch(); printf ("\nVoulez vous continuer (Non=0)? "); scanf ("%d",&test); } while (test!=0); }

___________________________________________________________________
DI GALLO Frdric Page 36 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

___________________________________________________________________
DI GALLO Frdric Page 37 01/04/01

Programmation Classique en C.doc ______________________________________________________________________________

___________________________________________________________________
DI GALLO Frdric Page 38 01/04/01

Vous aimerez peut-être aussi