Algorithmique et Langage - Pages de Michel Deloizy - Free
Algorithmique et Langage - Pages de Michel Deloizy - Free
Algorithmique et Langage - Pages de Michel Deloizy - Free
Create successful ePaper yourself
Turn your PDF publications into a flip-book with our unique Google optimized e-Paper software.
Licence L1<br />
<strong>Algorithmique</strong> <strong>et</strong> <strong>Langage</strong><br />
II22<br />
Cours<br />
Travaux dirigés<br />
Travaux pratiques<br />
M. <strong>Deloizy</strong> http://michel.<strong>de</strong>loizy.free.fr<br />
Édition du 15 janvier 2005
Introduction à l'informatique<br />
Notion d'algorithme<br />
Généralités<br />
Rappels<br />
M. <strong>Deloizy</strong> Informatique - Généralités 1<br />
M. <strong>Deloizy</strong> Informatique - Généralités 2<br />
Algorithme<br />
• Ensemble <strong>de</strong> règles opératoires propres à<br />
un calcul<br />
• Calcul, enchaînement <strong>de</strong>s actions<br />
nécessaires à l'accomplissement d'une<br />
tâche<br />
• P<strong>et</strong>it Robert :<br />
Métho<strong>de</strong> proposée pour le traitement d'un<br />
problème par un automate<br />
Humain ou machine Traitement systématique<br />
M. <strong>Deloizy</strong> Informatique - Généralités 3<br />
Exemple d'algorithme<br />
• Rec<strong>et</strong>te <strong>de</strong> cuisine :<br />
– Nom <strong>de</strong> la rec<strong>et</strong>te<br />
– Ingrédients<br />
– Réalisation<br />
… Gâteau au yaourt …<br />
M. <strong>Deloizy</strong> Informatique - Généralités 4<br />
1
Définition d'un algorithme<br />
• But recherché<br />
– (que doit faire l'algorithme ?)<br />
… un gâteau au yaourt pour 6 personnes<br />
• Outils disponibles<br />
– Opérateurs, données, règles associées<br />
Yaourts, œufs, sucre, huile, sel, levure, moule, four<br />
• Enchaînement <strong>de</strong>s actions<br />
– Ordre <strong>de</strong> traitement<br />
Description <strong>de</strong> la séquence d'actions nécessaires à la<br />
réalisation <strong>de</strong> la rec<strong>et</strong>te<br />
Algorithme universel<br />
• Non lié à un langage <strong>de</strong> programmation<br />
• Non lié à une machine<br />
Mais<br />
• Peut être plus ou moins adapté à un type<br />
d'automate<br />
M. <strong>Deloizy</strong> Informatique - Généralités 5<br />
M. <strong>Deloizy</strong> Informatique - Généralités 6<br />
Exemple : Multiplication<br />
Multiplication à la Russe<br />
• Classique :<br />
34 x 15 → 510<br />
Nécessite la connaissance <strong>de</strong>s tables <strong>de</strong><br />
multiplication<br />
34<br />
17<br />
8<br />
4<br />
2<br />
1<br />
15<br />
30<br />
60<br />
120<br />
240<br />
480<br />
510<br />
Uniquement<br />
<strong>de</strong>s multiplications<br />
par 2,<br />
<strong>de</strong>s divisions par 2<br />
<strong>et</strong> <strong>de</strong>s additions<br />
→ adapté au calcul<br />
par <strong>de</strong>s circuits<br />
logiques<br />
M. <strong>Deloizy</strong> Informatique - Généralités 7<br />
M. <strong>Deloizy</strong> Informatique - Généralités 8<br />
2
Algorithmes multiples<br />
• Pour résoudre une application, il existe<br />
souvent plusieurs algorithmes.<br />
Le choix sera fait selon :<br />
– La rapidité d'exécution<br />
– La facilité <strong>de</strong> mise en œuvre par l'automate<br />
– Le type <strong>de</strong> données à traiter<br />
Support matériel<br />
Architecture d'un ordinateur<br />
M. <strong>Deloizy</strong> Informatique - Généralités 9<br />
M. <strong>Deloizy</strong> Informatique - Généralités 10<br />
Architecture d'un ordinateur<br />
• 3 éléments :<br />
– Le processeur<br />
– La mémoire<br />
– Les périphériques<br />
Le processeur<br />
• Le cœur du système<br />
• Rôle :<br />
– Traiter <strong>de</strong>s informations binaires<br />
• Lire <strong>de</strong>s informations <strong>de</strong>puis la mémoire<br />
• Écrire <strong>de</strong>s informations dans la mémoire<br />
• Réaliser <strong>de</strong>s opérations élémentaires sur infos.<br />
• Traitement <strong>de</strong>s informations selon un "programme"<br />
→ lu <strong>de</strong> manière séquentielle au rythme d'une horloge<br />
M. <strong>Deloizy</strong> Informatique - Généralités 11<br />
M. <strong>Deloizy</strong> Informatique - Généralités 12<br />
3
La mémoire<br />
• Stockage<br />
– Des informations<br />
– Des programmes<br />
•ROM<br />
– Données permanentes<br />
•RAM<br />
– Données temporaires<br />
– Utilisée par le processeur pour le traitement<br />
<strong>de</strong>s données <strong>et</strong> <strong>de</strong>s programmes<br />
La mémoire <strong>de</strong> masse<br />
• Stockage <strong>de</strong> gran<strong>de</strong> capacité<br />
– Ban<strong>de</strong>s magnétiques, disques, CD, DVD<br />
• Mémoire non volatile<br />
• Réinscriptible<br />
• Pas d'accès direct par le processeur<br />
→ mémoire "lente" (quelques ms)<br />
RAM : quelques ns<br />
M. <strong>Deloizy</strong> Informatique - Généralités 13<br />
M. <strong>Deloizy</strong> Informatique - Généralités 14<br />
Les Périphériques<br />
• Organes <strong>de</strong> communication<br />
• Disposés entre le processeur <strong>et</strong> le mon<strong>de</strong><br />
extérieur<br />
• Perm<strong>et</strong>tent les échanges avec :<br />
– L'utilisateur<br />
– Une autre machine<br />
• Exemples :<br />
– Écran, clavier, ports série ou parallèle, USB,<br />
réseaux, mo<strong>de</strong>m<br />
Le système d'exploitation<br />
• Perm<strong>et</strong> le dialogue entre l'utilisateur <strong>et</strong> la<br />
machine<br />
• Gestion <strong>de</strong>s ressources <strong>de</strong> l'ordinateur<br />
• Scrutation permanente <strong>de</strong>s sollicitations <strong>de</strong><br />
l'environnement<br />
→ Contient un interpréteur <strong>de</strong> comman<strong>de</strong>s<br />
• Exemples :<br />
–MS-DOS<br />
– Windows<br />
–Unix, …<br />
M. <strong>Deloizy</strong> Informatique - Généralités 15<br />
M. <strong>Deloizy</strong> Informatique - Généralités 16<br />
4
Les outils <strong>de</strong> développement<br />
• L'éditeur <strong>de</strong> texte<br />
• L'assembleur<br />
• Le compilateur<br />
• L'éditeur <strong>de</strong> liens<br />
• Le débuggeur<br />
• L'interpréteur<br />
M. <strong>Deloizy</strong> Informatique - Généralités 17<br />
L'éditeur <strong>de</strong> textes<br />
• Programme perm<strong>et</strong>tant la saisie du texte<br />
contenant le programme source<br />
– Éditeur pleine page<br />
– Enregistrement <strong>et</strong> récupération <strong>de</strong> fichier en<br />
mémoire <strong>de</strong> masse<br />
– Modification aisée du texte<br />
– Outils divers :<br />
• Copier-coller<br />
• Recherche, remplacement<br />
– Ai<strong>de</strong> à la lisibilité (in<strong>de</strong>ntation, coloration, …)<br />
M. <strong>Deloizy</strong> Informatique - Généralités 18<br />
Le co<strong>de</strong> machine<br />
• Programme "lu" par le processeur : binaire<br />
→ co<strong>de</strong> machine<br />
Exemple :<br />
B6 30 00 charger A par cont. 3000H<br />
8B 05 ajouter 05H à A<br />
F7 30 01 ranger le résultat en 3001H<br />
• Programmation longue <strong>et</strong> fastidieuse<br />
• Très peu lisible, risque d'erreurs élevé<br />
M. <strong>Deloizy</strong> Informatique - Généralités 19<br />
L'assembleur<br />
• Écriture du co<strong>de</strong> machine en texte clair<br />
→ utilisation <strong>de</strong> mnémoniques<br />
Exemple :<br />
LDAA $3000 charger A par cont. 3000H<br />
ADDA #$05<br />
ajouter 05H à A<br />
STAA $3001 ranger le résultat en 3001H<br />
• Saisie du texte par un éditeur <strong>de</strong> textes<br />
• Texte traduit en co<strong>de</strong> machine par un<br />
programme : l'assembleur<br />
→ Amélioration <strong>de</strong> la lisibilité<br />
M. <strong>Deloizy</strong> Informatique - Généralités 20<br />
5
Problèmes liés à l'assembleur<br />
• <strong>Langage</strong> du processeur<br />
– Très différent du langage naturel<br />
– Pas <strong>de</strong> gestion évoluée <strong>de</strong>s données<br />
– Pas <strong>de</strong> système <strong>de</strong> protection<br />
– Propre à chaque processeur<br />
→ Maintenance difficile<br />
→ Portabilité nulle<br />
Mais :<br />
gran<strong>de</strong> efficacité (pour un bon programmeur)<br />
Le compilateur<br />
•But :<br />
– S'affranchir du type <strong>de</strong> processeur<br />
– S'affranchir <strong>de</strong> l'environnement matériel <strong>et</strong><br />
logiciel<br />
– Écriture <strong>de</strong>s programmes en langage naturel<br />
→ langage évolué<br />
• Compilateur :<br />
– Traduit le texte (source) en co<strong>de</strong> machine<br />
M. <strong>Deloizy</strong> Informatique - Généralités 21<br />
M. <strong>Deloizy</strong> Informatique - Généralités 22<br />
Utilisation d'un compilateur<br />
• Bonne lisibilité <strong>de</strong>s programmes<br />
• Bonne portabilité<br />
• Gestion <strong>de</strong> données complexes<br />
• Gestion <strong>de</strong> la mémoire du système<br />
• Gestion standard <strong>de</strong>s périphériques<br />
• Rapidité d'écriture <strong>de</strong>s programmes<br />
• Maintenance aisée<br />
En + :<br />
• Optimisation <strong>de</strong>s programmes<br />
• Systèmes <strong>de</strong> protection, gar<strong>de</strong>-fous<br />
Défaut <strong>de</strong>s compilateurs<br />
• <strong>Langage</strong> évolué très différent du langage<br />
machine<br />
→ traduction parfois difficile<br />
→ surco<strong>de</strong> parfois excessif<br />
– Exécutable volumineux, lent<br />
• Vrai avec processeurs anciens ou peu<br />
performants<br />
M. <strong>Deloizy</strong> Informatique - Généralités 23<br />
M. <strong>Deloizy</strong> Informatique - Généralités 24<br />
6
L'éditeur <strong>de</strong> liens<br />
• Création d'un programme :<br />
– Écriture d'un programme source (texte)<br />
Compilation<br />
– Programme obj<strong>et</strong> (binaire, co<strong>de</strong> machine<br />
incompl<strong>et</strong>)<br />
Éditeur <strong>de</strong> liens<br />
Bibliothèques personnelles<br />
Bibliothèques du langage<br />
– Programme exécutable (binaire autonome)<br />
Utilisation <strong>de</strong> l'éditeur <strong>de</strong> liens<br />
• Bibliothèques personnelles<br />
→ extension du langage à sa convenance<br />
• Portions <strong>de</strong> programmes réutilisables<br />
• Dépannage ou amélioration d'une<br />
bibliothèque<br />
⇒ dépannage ou amélioration <strong>de</strong> tous les<br />
programmes qui en dépen<strong>de</strong>nt<br />
M. <strong>Deloizy</strong> Informatique - Généralités 25<br />
M. <strong>Deloizy</strong> Informatique - Généralités 26<br />
Le débuggeur<br />
• Outil perm<strong>et</strong>tant le dépannage <strong>de</strong>s programmes<br />
(exécutables)<br />
– Consultation <strong>de</strong>s données<br />
– Exécution instruction par instruction<br />
– Points d'arrêt<br />
• Souvent intégré dans<br />
IDE (Integrated Development Environment)<br />
ou EDE (Embed<strong>de</strong>d Development Environment)<br />
→ Éditeur + Compilateur + Éditeur <strong>de</strong> liens + Débugger<br />
M. <strong>Deloizy</strong> Informatique - Généralités 27<br />
L'interpréteur<br />
• Exécute le programme pendant la lecture<br />
du co<strong>de</strong> source<br />
– Très lent (chaque instruction est interprétée<br />
puis exécutée à chaque utilisation)<br />
– Présence <strong>de</strong> la totalité <strong>de</strong>s bibliothèques du<br />
langage indispensable<br />
– Le programme n'est pas autonome (exécuté<br />
sous le contrôle <strong>de</strong> l'interpréteur)<br />
– Pas d'éditeur <strong>de</strong> liens<br />
– Pas d'optimisation <strong>de</strong> co<strong>de</strong><br />
M. <strong>Deloizy</strong> Informatique - Généralités 28<br />
7
Représentation <strong>de</strong>s données<br />
Données utilisées en<br />
informatique<br />
• Types <strong>de</strong>s données<br />
– Choisi en fonction <strong>de</strong> l'utilisation<br />
Exemples :<br />
• Comptage d'un nombre d'étudiants<br />
• Calcul du sinus d'un angle<br />
• Écriture d'un texte<br />
• Données codées en binaire<br />
– Pour le traitement par le processeur<br />
– Définition d'un mo<strong>de</strong> <strong>de</strong> rangement en mémoire pour<br />
chaque type <strong>de</strong> donnée<br />
• Limitations liées au codage utilisé<br />
M. <strong>Deloizy</strong> Informatique - Généralités 29<br />
M. <strong>Deloizy</strong> Informatique - Généralités 30<br />
Le type entier<br />
Valeurs limites<br />
•Signé :<br />
– …, -2, -1, 0, 1, 2, …<br />
• Non signé<br />
– 0, 1, 2, …<br />
• Traitement <strong>de</strong> données entières<br />
– Adapté aux énumérations<br />
Codage<br />
8 bits<br />
16 bits<br />
32 bits<br />
Signé<br />
min max<br />
-128 127<br />
80 H 7F H<br />
-32768<br />
-2147483648<br />
32767<br />
2147483647<br />
min<br />
0<br />
0 H<br />
0<br />
0<br />
Non signé<br />
max<br />
255<br />
FF H<br />
65535<br />
4294967295<br />
M. <strong>Deloizy</strong> Informatique - Généralités 31<br />
Rem. : En représentation signée, le signe du nombre est donné<br />
par le bit <strong>de</strong> poids le plus fort (1 pour négatif)<br />
M. <strong>Deloizy</strong> Informatique - Généralités 32<br />
8
Opérations possibles<br />
• Arithmétiques<br />
! Addition (+)<br />
! Soustraction (-)<br />
! Multiplication(*)<br />
! Division entière (/)<br />
! Modulo (%) Reste <strong>de</strong> la division entière<br />
Opérations possibles<br />
• Logiques (bit à bit)<br />
! ET logique (&)<br />
! OU logique (|)<br />
! OU exclusif (^)<br />
! Complément à 1 (~)<br />
• Comparaisons<br />
! ==, , =, !=<br />
M. <strong>Deloizy</strong> Informatique - Généralités 33<br />
M. <strong>Deloizy</strong> Informatique - Généralités 34<br />
• ±nnn<br />
! 12, -5, +3, 0<br />
Notation<br />
Utilisation<br />
• Intérêt <strong>de</strong>s entiers :<br />
– Valeurs exactes, pas d'imprécision<br />
– Adaptés au comptage, dénombrement<br />
• Inconvénient :<br />
– Dynamique limitée<br />
• Pas <strong>de</strong> très grand nombre<br />
• Pas <strong>de</strong> très p<strong>et</strong>it nombre<br />
– Inadaptés au calcul scientifique<br />
M. <strong>Deloizy</strong> Informatique - Généralités 35<br />
M. <strong>Deloizy</strong> Informatique - Généralités 36<br />
9
Le type booléen<br />
• Résultat d'une expression logique<br />
• 2 valeurs possibles :<br />
– Vrai ou Faux<br />
• Opérateurs :<br />
– ET, OU, NON : résultat booléen<br />
Ex. : Vrai OU Faux → Vrai<br />
Vrai ET Vrai → Vrai<br />
NON Vrai → Faux<br />
• Codage :<br />
– 1 bit suffit<br />
M. <strong>Deloizy</strong> Informatique - Généralités 37<br />
Le type à virgule flottante<br />
• Nombres réels (positifs <strong>et</strong> négatifs)<br />
• Notation mantisse – exposant<br />
• Perm<strong>et</strong>tent une gran<strong>de</strong> dynamique :<br />
– Très p<strong>et</strong>ites valeurs (Ex. : ±1.6 10 -19 )<br />
– Très gran<strong>de</strong>s valeurs (Ex. : 25.2 10 47 )<br />
• Problème d'imprécision :<br />
– Ex. : entre 2.0 <strong>et</strong> 2.1 → infinité <strong>de</strong> valeurs<br />
codage machine ⇒ nombre <strong>de</strong> valeurs fini<br />
– Présence d'arrondis<br />
M. <strong>Deloizy</strong> Informatique - Généralités 38<br />
Codage<br />
• Exemple <strong>de</strong> codage sur 32 bits (IEEE)<br />
– Mantisse sur 24 bits<br />
– Exposant sur 8 bits<br />
± m . 2 e<br />
! S : signe (1 : négatif, 0 : positif)<br />
! m : mantisse (1 ≤ m < 2) ⇒ m = 1.xxxxx<br />
! e : exposant (-128 ≤ e ≤ 127)<br />
! f : partie fractionnaire <strong>de</strong> la mantisse<br />
! e' : e+127 (1 ≤ e' ≤ 254)<br />
e'<br />
f<br />
S<br />
b 31 b 30 b 23 b 22<br />
… b 0<br />
M. <strong>Deloizy</strong> Informatique - Généralités 39<br />
Valeurs limites<br />
e'<br />
f<br />
S<br />
b 31 b 30 b 23 b 22<br />
… b 0<br />
• Valeur la plus p<strong>et</strong>ite positive :<br />
–S = 0<br />
–e' = 1 ⇒ e = -126<br />
–f = 0 ⇒ m = 1.0<br />
V min = 1.0 2 -126 ≈ 1.175 10 -38<br />
• Valeur la plus gran<strong>de</strong> positive :<br />
–S = 0<br />
– e' = 254 ⇒ e = 127<br />
– f = 0.11111… ⇒ m = 1.11111… = 2.0 – 2 -23<br />
V max = (2.0 – 2 -23 ) 2 127 ≈ 3.403 10 38<br />
M. <strong>Deloizy</strong> Informatique - Généralités 40<br />
10
Résolution<br />
• Valeur suivante <strong>de</strong> 1.0 :<br />
1.0 + 2 -23 = 1.0 + 1.2 10 -7<br />
→ 6 chiffres significatifs<br />
Valeurs particulières<br />
± m . 2 e avec m>1 ne perm<strong>et</strong> pas <strong>de</strong> co<strong>de</strong>r 0.0<br />
• Si e' = 0 → codage <strong>de</strong> 0.0<br />
• Si e' = 255 → codage <strong>de</strong> ±NAN<br />
M. <strong>Deloizy</strong> Informatique - Généralités 41<br />
M. <strong>Deloizy</strong> Informatique - Généralités 42<br />
• Sur 64 bits (8 oct<strong>et</strong>s) :<br />
– Mantisse sur 52 bits<br />
– Exposant sur 11 bits<br />
– Signe sur 1 bit<br />
Autres codages<br />
– 15 chiffres significatifs<br />
– Valeurs limites ≈ 10 ±308<br />
Opérations possibles<br />
• Arithmétiques<br />
! Addition (+)<br />
! Soustraction (-)<br />
! Multiplication(*)<br />
! Division (/)<br />
• Comparaisons<br />
! ==, , =, !=<br />
• Sur 80 bits → 18 chiffres significatifs, ≈ 10 ±4932 M. <strong>Deloizy</strong> Informatique - Généralités 44<br />
M. <strong>Deloizy</strong> Informatique - Généralités 43<br />
11
Notation<br />
Forme générale :<br />
±dd.ddE±xx ⇔ ±dd.dd 10 ±xx<br />
• ±nnn.nnn<br />
! 2.0, -1.432, +4.5, 0.0<br />
• ±.nnn ou ± nnn.<br />
! 1. , -.2, 0.<br />
• ± nnE ±nn ou ± nne ±nn<br />
! 1E3, 5.22e-23, +3.2E-2<br />
M. <strong>Deloizy</strong> Informatique - Généralités 45<br />
Le type caractère<br />
• Caractères codés pour représentation en<br />
machine<br />
• 7 bits suffisent (128 caractères)<br />
• Exemple <strong>de</strong> co<strong>de</strong> : ASCII<br />
– American Standard Co<strong>de</strong> for Information<br />
Interchange<br />
– Défini par ANSI (American National Standard<br />
Institute)<br />
M. <strong>Deloizy</strong> Informatique - Généralités 46<br />
Codage ASCII<br />
• Contient :<br />
– L<strong>et</strong>tres minuscules <strong>et</strong> majuscules (ordre<br />
alphabétique) : 2x26 caractères<br />
– Chiffres (ordre croissant <strong>de</strong> 0 à 9)<br />
– Ponctuations, caractères typographiques, …<br />
– Caractères <strong>de</strong> contrôle (co<strong>de</strong>s 0 à 31)<br />
• Exemples :<br />
– 'A' = 65, 'B' = 66, 'Z' = 90, 'a' = 97, '0' = 48<br />
– CR = 13, LF = 10, TAB = 9, FF = 12, BEL = 7<br />
Autres codages<br />
• EBCDIC (IBM)<br />
• ANSI (jeux <strong>de</strong> caractères internationaux)<br />
• ASCII étendu<br />
Souvent sur 1 oct<strong>et</strong><br />
Rem. : le langage informatique prend en charge le<br />
codage (pas nécessaire <strong>de</strong> le connaître)<br />
M. <strong>Deloizy</strong> Informatique - Généralités 47<br />
M. <strong>Deloizy</strong> Informatique - Généralités 48<br />
12
Notation <strong>et</strong> opérations possibles<br />
• Notation :<br />
– 'X', '0', '2'<br />
– '\r', '\n', '\t'<br />
– '\\', '\'' (caractère d'échappement : \ )<br />
• Opérations possibles :<br />
– Additions, soustraction avec <strong>de</strong>s entiers<br />
Ex. : 'A' + 1 → 'B'<br />
– Comparaisons<br />
Ex. : 'A' < 'E'<br />
Chaînes <strong>de</strong> caractères<br />
• Ensemble ordonné <strong>de</strong> caractères<br />
représentant un mot, une phrase.<br />
• Particularité :<br />
– Nombre <strong>de</strong> caractères variable<br />
→ Taille très variable<br />
M. <strong>Deloizy</strong> Informatique - Généralités 49<br />
M. <strong>Deloizy</strong> Informatique - Généralités 50<br />
Codage<br />
• Codages possibles :<br />
–
Le type adresse<br />
• Données <strong>et</strong> programmes<br />
rangés en mémoire<br />
→ Chaque donnée,<br />
chaque instruction a une<br />
adresse propre<br />
→ Le processeur accè<strong>de</strong><br />
aux données <strong>et</strong> aux<br />
instructions grâce à leur<br />
adresse<br />
Contenu<br />
adresse mémoire<br />
C32C H 2A H<br />
C32D H F0 H<br />
C32E H 12 H<br />
C32F H 45 H<br />
C330 H C5 H<br />
Variable<br />
toto<br />
c1<br />
c2<br />
x<br />
Indirection<br />
• Une donnée peut<br />
contenir une adresse<br />
→ pointe sur une autre adresse<br />
donnée<br />
C32C H<br />
→ Ex. : ptr pointe sur c2 C32D H<br />
→ Pointeur<br />
C32E H<br />
→ On peut modifier c2 <strong>de</strong> C32F H<br />
manière indirecte en C330<br />
agissant sur ptr<br />
H<br />
→ Indirection<br />
Contenu<br />
mémoire<br />
C3 H<br />
2F H<br />
12 H<br />
45 H<br />
C5 H<br />
Variable<br />
ptr<br />
c1<br />
c2<br />
x<br />
Remarque : On peut avoir <strong>de</strong>s indirections multiples<br />
M. <strong>Deloizy</strong> Informatique - Généralités 53<br />
M. <strong>Deloizy</strong> Informatique - Généralités 54<br />
Les tableaux<br />
• Données rangées <strong>de</strong> manière contiguë en<br />
mémoire<br />
• Données indicées (vecteurs)<br />
• Tout type <strong>de</strong> donnée peut être organisé en<br />
tableau<br />
Exemple :<br />
• Caractéristiques d'un tableau :<br />
– Adresse du 1er élément<br />
– Nombre d'éléments<br />
– Type <strong>de</strong>s données contenues<br />
Constantes<br />
• Données non modifiables<br />
• Utilisées dans <strong>de</strong>s expressions<br />
• Exemple :<br />
P = 2.0 * PI * Rayon<br />
Constantes<br />
t 0 t 1 t 2 t n<br />
M. <strong>Deloizy</strong> Informatique - Généralités 56<br />
M. <strong>Deloizy</strong> Informatique - Généralités 55<br />
14
Constantes explicites<br />
• Valeur écrite explicitement<br />
– L'écriture indique le type <strong>de</strong> la constante :<br />
• 2, -3 : entiers<br />
• 1.0, 2E4 : virgules flottantes<br />
• 'z', '2' : caractères<br />
• "TOTO" : chaîne <strong>de</strong> caractères<br />
M. <strong>Deloizy</strong> Informatique - Généralités 57<br />
Constantes prédéfinies<br />
• Utilisées par l'intermédiaire d'un nom <strong>de</strong><br />
symbole<br />
• Utilisation i<strong>de</strong>ntique à constante explicite<br />
• Avantages :<br />
– Perm<strong>et</strong> une meilleure lisibilité<br />
– Facilite la maintenance<br />
– Évite <strong>de</strong>s écritures & modifications multiples<br />
→ réduit le risque d'erreurs<br />
Exemple : constante TVA = 0.196<br />
Pull_ttc = Pull_ht*(1+TVA)<br />
Chemise_ttc = Chemise_ht*(1+TVA)<br />
M. <strong>Deloizy</strong> Informatique - Généralités 58<br />
Constitution d'un programme<br />
Écriture d'un programme<br />
• Ensemble <strong>de</strong> fonctions ou procédures<br />
• Une fonction particulière :<br />
– démarrage du programme, point d'entrée<br />
Principes <strong>de</strong> base<br />
M. <strong>Deloizy</strong> Informatique - Généralités 59<br />
M. <strong>Deloizy</strong> Informatique - Généralités 60<br />
15
Fonctions<br />
• Composées d'instructions<br />
– Exécutées séquentiellement<br />
• Instructions :<br />
– Expressions, ex. : y=a+b, y=sin(a)<br />
– Contrôle <strong>de</strong> déroulement, ex. : si y
Classe d'allocation<br />
• Façon dont la donnée est créée par le<br />
compilateur :<br />
– Allocation statique :<br />
• Donnée créée au chargement du programme<br />
• Emplacement fixe pendant durée d'exécution<br />
• Valeur laissée précé<strong>de</strong>mment r<strong>et</strong>rouvée à chaque<br />
accès<br />
– Allocation dynamique :<br />
• Donnée créée lors <strong>de</strong> la déclaration<br />
• Valeur initiale aléatoire<br />
• Donnée détruite en fin d'utilisation<br />
Portée <strong>de</strong>s données<br />
• Données connues par la totalité du<br />
programme ou par une portion seulement :<br />
– Donnée globale<br />
• Toutes les fonctions du programme peuvent y<br />
accé<strong>de</strong>r<br />
– Donnée locale<br />
• Définie pour une portion <strong>de</strong> programme (par<br />
exemple une fonction)<br />
• Inconnue hors <strong>de</strong> c<strong>et</strong>te portion<br />
M. <strong>Deloizy</strong> Informatique - Généralités 65<br />
M. <strong>Deloizy</strong> Informatique - Généralités 66<br />
Règles <strong>de</strong> portée<br />
• Deux variables ne peuvent pas avoir le<br />
même nom dans la même zone <strong>de</strong> portée<br />
• Si une donnée locale porte le même nom<br />
qu'une donnée globale, la donnée globale<br />
<strong>de</strong>vient inaccessible<br />
→ masquage <strong>de</strong> la donnée globale<br />
Structures conditionnelles<br />
Contrôle du déroulement du<br />
programme<br />
M. <strong>Deloizy</strong> Informatique - Généralités 67<br />
M. <strong>Deloizy</strong> Informatique - Généralités 68<br />
17
Structure conditionnelle simple<br />
• Si alors …<br />
finsi<br />
if (x
Structure itérative Pour<br />
• Pour jusqu'à faire … FinPour<br />
– Facilité d'écriture<br />
– Peut être remplacé par Tant que<br />
for(i=0; i
Affectations autorisées<br />
• Entier ← Entier<br />
← Virgule flottante<br />
← Caractère<br />
• Virgule flottante ← Virgule flottante<br />
← Entier<br />
• Caractère ← Caractère<br />
← Entier<br />
• Booléen ← Booléen<br />
• Adresse ← Adresse<br />
Expressions<br />
• Arithmétiques ou logiques<br />
• Utilisation d'opérateurs :<br />
– Lecture <strong>de</strong> gauche à droite<br />
– Prise en compte <strong>de</strong>s priorités<br />
Ex. : y = 2*a + 3*b ⇔ y = (2*a) + (3*b)<br />
– Utilisation <strong>de</strong> ( ) pour forcer la priorité<br />
• Priorités classiques :<br />
! * <strong>et</strong> / ont la même priorité<br />
! - <strong>et</strong> + ont la même priorité<br />
! * <strong>et</strong> / sont prioritaires sur + <strong>et</strong> –<br />
– Les opérateurs logiques utilisent l'algèbre <strong>de</strong> Boole<br />
M. <strong>Deloizy</strong> Informatique - Généralités 77<br />
M. <strong>Deloizy</strong> Informatique - Généralités 78<br />
Exemple :<br />
y = a / 2 / x + 3* b / 2<br />
Priorités<br />
⇔<br />
y =<br />
2⋅<br />
Quand appel <strong>de</strong> fonction :<br />
– Arguments évalués avant l'appel<br />
– Fonction ⇔ variable calculée<br />
Ex. : y = 2 * sin(x)<br />
y = sin(a + acos(b)*2)<br />
a<br />
x<br />
3⋅b<br />
+<br />
2<br />
Opérateurs logiques<br />
• Utilisés dans les structures conditionnelles<br />
• Utilisent l'algèbre <strong>de</strong> Boole<br />
• ==, !=, , =, &&, ||, !<br />
Exemple :<br />
if( !( (x'z') ) ) …<br />
A B<br />
A + B = A⋅<br />
B<br />
if( (x>='a') && (x
Utilité <strong>de</strong>s fonctions<br />
Fonctions<br />
• Décomposer un problème complexe en sous problèmes<br />
plus simples<br />
– Analyse <strong>de</strong>scendante<br />
• Éviter la répétition <strong>de</strong> lignes <strong>de</strong> programmes<br />
• Améliorer la lisibilité<br />
• Faciliter la maintenance (constitution <strong>de</strong> bibliothèques)<br />
• Renvoie une valeur dépendant <strong>de</strong> paramètres transmis<br />
• Fonction qui ne renvoie rien :<br />
– Procédure, sous-programme<br />
M. <strong>Deloizy</strong> Informatique - Généralités 81<br />
M. <strong>Deloizy</strong> Informatique - Généralités 82<br />
Définition d'une fonction<br />
• À définir :<br />
– Nom <strong>de</strong> la fonction<br />
– Type <strong>de</strong> la valeur renvoyée<br />
– Type <strong>de</strong>s paramètres transmis<br />
Exemples : Utilisation :<br />
double sin(double x)<br />
y = sin(3.0);<br />
void clrscr(void) clrscr( );<br />
double pow(double y, double x) y = pow(2.0, 0.5)/2.0;<br />
Fonctions <strong>et</strong> paramètres<br />
• Lors <strong>de</strong> l'appel d'une fonction, les paramètres :<br />
– Sont tout d'abord évalués<br />
– Sont transmis dans l'ordre <strong>de</strong> leur écriture<br />
→ le type doit être compatible<br />
Exemple :<br />
void fct(int a, double x) {<br />
…<br />
}<br />
a, x : variables locales à fct<br />
…<br />
fct(3,2.0*sin(1.0));<br />
M. <strong>Deloizy</strong> Informatique - Généralités 83<br />
M. <strong>Deloizy</strong> Informatique - Généralités 84<br />
21
Transmission par valeur<br />
• La valeur du paramètre est recopiée<br />
→ Valeur initiale du paramètre (variable locale <strong>de</strong> la<br />
fonction)<br />
int somme(int a, int b) {<br />
int s;<br />
s = a+b;<br />
(15)<br />
r<strong>et</strong>urn s;<br />
}<br />
…<br />
X = somme(2, 5*3);<br />
Inconvénients <strong>de</strong> la transmission<br />
par valeur<br />
• Paramètre encombrant (ex. : tableau)<br />
• Une fonction ne renvoie qu'une valeur<br />
M. <strong>Deloizy</strong> Informatique - Généralités 85<br />
M. <strong>Deloizy</strong> Informatique - Généralités 86<br />
Transmission par référence<br />
Pointeurs<br />
• On transm<strong>et</strong> l'adresse du paramètre plutôt que<br />
sa valeur<br />
→ utilisation d'un pointeur (type adresse)<br />
int v;<br />
int *p;<br />
p = &v;<br />
v est un entier<br />
p est l'adresse d'un entier (*p : entier)<br />
p prend comme valeur l'adresse <strong>de</strong> v<br />
Pour accé<strong>de</strong>r à v, on utilise la notation *p<br />
→ signifie : l'entier pointé par p (ici : v)<br />
Pour charger 5 dans v, on peut donc écrire :<br />
v = 5<br />
*p = 5<br />
*(&v) = 5<br />
M. <strong>Deloizy</strong> Informatique - Généralités 87<br />
M. <strong>Deloizy</strong> Informatique - Généralités 88<br />
22
Pointeurs <strong>et</strong> fonctions<br />
int ProdQuot(int a, int b, int *p, int *q) {<br />
*p = a * b;<br />
if (b != 0) r<strong>et</strong>urn 0;<br />
*q = a / b;<br />
r<strong>et</strong>urn 1;<br />
}<br />
int main( ) {<br />
int u, v, x;<br />
x = 3;<br />
if (ProdQuot(x,2,&u,&v) == 0) {<br />
printf("%d x 2 = %d\n", x, u);<br />
}<br />
else {<br />
printf("%d x 2 = %d <strong>et</strong> %d / 2 =<br />
%d\n",x,u,x,v);<br />
}<br />
r<strong>et</strong>urn 0;<br />
}<br />
M. <strong>Deloizy</strong> Informatique - Généralités 89<br />
Fonctions réentrantes<br />
• Fonction exécutée plusieurs fois simultanément<br />
→ appelée <strong>de</strong> nouveau pendant son exécution<br />
– Systèmes multi-tâches<br />
– Interruptions<br />
• Contrainte :<br />
– Pas <strong>de</strong> donnée statique<br />
– Utilisation <strong>de</strong> données dynamiques<br />
→ Nouvelles données à chaque déclaration<br />
→ Données propres à chaque appel <strong>de</strong> fonction<br />
M. <strong>Deloizy</strong> Informatique - Généralités 90<br />
Fonctions récursives<br />
• Fonction qui se rappelle elle-même<br />
• L'appel peut être direct ou non<br />
• Particularités :<br />
– Fonctions réentrantes<br />
– Un point <strong>de</strong> sortie doit être prévu<br />
• Intérêt :<br />
– Écriture con<strong>de</strong>nsée <strong>et</strong> rapi<strong>de</strong> <strong>de</strong> programmes<br />
• Inconvénients :<br />
– Peu efficace à l'exécution<br />
– Gourmand en ressources<br />
M. <strong>Deloizy</strong> Informatique - Généralités 91<br />
<strong>Langage</strong> C<br />
M. <strong>Deloizy</strong> Informatique - Généralités 92<br />
23
Histoire<br />
<strong>Langage</strong> C<br />
C ANSI<br />
Brian KERNIGHAN & Dennis RITCHIE<br />
! Principes issus du BCPL <strong>et</strong> du B (1970)<br />
→ premier système UNIX<br />
! 1978 : Parution du livre "Le langage C"<br />
! Souvent associé à UNIX (écrit(<br />
en C)<br />
! Lié à aucune machine<br />
Lié à aucun système d'exploitation<br />
! 1988 : C norme ANSI<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C 1<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
2<br />
Intérêt du langage<br />
! <strong>Langage</strong> non spécifique (généraliste)<br />
! Bonne portabilité<br />
! Bonne efficacité (peu <strong>de</strong> sur-co<strong>de</strong><br />
co<strong>de</strong>)<br />
! Base du C++ (obj<strong>et</strong>)<br />
Constitution d’un<br />
programme C<br />
Programme<br />
Module<br />
1<br />
Module<br />
2<br />
Module<br />
Fonction1( ) {<br />
...<br />
}<br />
Module<br />
n<br />
Fichier .c<br />
(texte)<br />
Fonction1( ) {<br />
...<br />
}<br />
main( ) {<br />
...<br />
}<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
3<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
4<br />
1
Syntaxe<br />
Mots clés<br />
! Commentaires.<br />
! /* Ceci est un commentaire */<br />
! Noms <strong>de</strong> symboles.<br />
! Symboles autorisés :<br />
! toto Toto<br />
t123<br />
_tx_<br />
_12 ___<br />
! Symboles non autorisés :<br />
! 12_ 2t<br />
été m% bon jour<br />
! Minuscules <strong>et</strong> majuscules.<br />
! Les minuscules <strong>et</strong> majuscules sont différenciés en C.<br />
a<br />
auto<br />
continue<br />
enum<br />
if<br />
short<br />
switch<br />
volatile<br />
break<br />
<strong>de</strong>fault<br />
extern<br />
int<br />
signed<br />
type<strong>de</strong>f<br />
while<br />
case<br />
do<br />
float<br />
long<br />
sizeof<br />
union<br />
char<br />
double<br />
for<br />
register<br />
static<br />
unsigned<br />
const<br />
else<br />
goto<br />
r<strong>et</strong>urn<br />
struct<br />
void<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
5<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
6<br />
! Les types <strong>de</strong> base<br />
! char :<br />
Types <strong>de</strong> variables<br />
! Caractères (8 bits).<br />
! Entier court (signé par défaut).<br />
! Type <strong>de</strong> données <strong>de</strong> taille élémentaire.<br />
! int :<br />
! Entier (signé par défaut).<br />
! Type pris par défaut.<br />
! Au moins 16 bits.<br />
! float :<br />
! Nombre en virgule flottante.<br />
Types dérivés<br />
! unsigned char<br />
! signed char<br />
! unsigned int ou unsigned<br />
! short<br />
! unsigned short<br />
! long int ou long<br />
! unsigned long int ou unsigned long<br />
! double<br />
! long double<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
7<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
8<br />
2
Dynamique <strong>de</strong>s nombres<br />
ENTIERS<br />
Valeur minimale Valeur maximale<br />
8 bits signé -128<br />
127<br />
8 bits non signé 0 255<br />
16 bits signé -32768<br />
32767<br />
16 bits non signé 0 65535<br />
32 bits signé -22 147 483 648 2 147 483 647<br />
32 bits non signé 0 4 294 967 295<br />
VIRGULE<br />
FLOTTANTE<br />
Dynamique <strong>de</strong>s nombres<br />
Chiffres<br />
significatifs<br />
Exposant<br />
min/max<br />
4 oct<strong>et</strong>s 7 ±38<br />
8 oct<strong>et</strong>s 15 ± 308<br />
10 oct<strong>et</strong>s 19 ± 4932<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
9<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
10<br />
Taille <strong>de</strong>s données<br />
! Si E représente l’encombrement mémoire d’un type :<br />
E(char) ≤ E(short) ≤ E(int<br />
int) ≤ E(long)<br />
E(float<br />
float) ≤ E(double) ≤ E(long double)<br />
! Opérateur sizeof.<br />
! Pas <strong>de</strong> type booléen.<br />
Résultat nul ⇒ faux<br />
Résultat non nul ⇒ vrai<br />
Types composés<br />
! les tableaux<br />
! les structures<br />
! les unions<br />
! Remarque :<br />
! On peut combiner les structures <strong>et</strong> les tableaux<br />
! " tableaux <strong>de</strong> structures<br />
! " structures contenant <strong>de</strong>s tableaux.<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
11<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
12<br />
3
Autres types<br />
! les types définis par le programmeur<br />
! type<strong>de</strong>f<br />
! void<br />
! type<strong>de</strong>f unsigned char byte;<br />
! type<strong>de</strong>f unsigned short word;<br />
! type<strong>de</strong>f unsigned long dword;<br />
Déclaration <strong>de</strong>s variables<br />
! char x ;<br />
⇒ x est un caractère<br />
(sur 8 bits : [-128…+127])[<br />
! int i, j, k ; ⇒ i, j <strong>et</strong> k sont <strong>de</strong>s entiers<br />
(sur 16 bits : [-32768…+32767])[<br />
! unsigned arthur ; ⇒ arthur est un entier non signé<br />
(sur 16 bits : [0…+65535])<br />
! unsigned char oct<strong>et</strong> ; ⇒ oct<strong>et</strong> est un caractère non signé<br />
(sur 8 bits : [0…+255])<br />
! char tab[10] ; ⇒ tab est un tableau pouvant contenir<br />
10 caractères<br />
! double f[5][3] ; ⇒ f est un tableau <strong>de</strong> 5 lignes<br />
<strong>et</strong> 3 colonnes (15 x double)<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
13<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
14<br />
Tableaux<br />
! Le premier élément d’un tableau est d’indice 0.<br />
! Rangement consécutif en mémoire (Ex. <strong>de</strong> tab[0] à<br />
tab[9])<br />
! Tableaux multi-dimensionnés<br />
: le <strong>de</strong>rnier indice « court »<br />
le plus vite :<br />
f[0][0], f[0][1], f[0][2], f[1][0], f[1][1], f[1][2], f[2][0], … , f[4][1], f[4][2]<br />
Constantes<br />
Types<br />
Écritures<br />
Exemples<br />
Caractère<br />
‘x’ ‘A’, ‘=’, ‘\\’,‘<br />
‘\’’‘<br />
Entier<br />
nnn ou ±nnn<br />
421, 0, -12, +456<br />
Entier exprimé en octal 0nnn ou ± 0nnn 0712, 010, -057<br />
Entier hexadécimal<br />
0xnn ou 0xNN<br />
0x4A, 0x00ff<br />
double<br />
± nnn.nn ou ± nnnE ± nn 1.0, -4., 3E4, 1.6e-19<br />
19<br />
Chaîne <strong>de</strong> caractères<br />
"xxxxxx"<br />
"Bonjour les amis"<br />
Remarque : \ est le caractère d‘échappement en C<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
15<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
16<br />
4
Constantes particulières<br />
Séquence<br />
Signification<br />
\r R<strong>et</strong>our chariot (en début <strong>de</strong> ligne).<br />
\n Saut à la ligne suivante. 0x0A<br />
\t Tabulation. 0x09<br />
\\ Caractère \<br />
\’ Caractère '<br />
\" Caractère "<br />
\xnn<br />
\ooo<br />
Exemple<br />
printf("<br />
("\rbonjour")<br />
printf("bonjour<br />
("bonjour\n") n")<br />
printf("Rés.<br />
("Rés.\tMoy.\n")<br />
Nombre hexadécimal<br />
Nombre octal (o : digit octal) \012,<br />
Résultat<br />
") bonjour<br />
bonjour!<br />
Rés.<br />
Moy. !<br />
printf("valeur : \\10\\\n")<br />
valeur : \10\!<br />
x='\''<br />
''-0x20<br />
x=39-32<br />
32 ⇒ x=7<br />
printf("Il dit : \"Bof!\"\n")<br />
Il dit : "Bof!" <br />
0x3B, 0xFA8 59, 4008<br />
012, \033<br />
10, 27<br />
Suffixe :<br />
Entier<br />
Virgule flottante<br />
Suffixes<br />
sans<br />
U ou u<br />
L ou l<br />
int<br />
unsigned int<br />
long<br />
double - long double<br />
! Exemples :<br />
12L :<br />
valeur 12 codée sur un type long<br />
40000u : codé sur un type unsigned int<br />
13.4 : constante double<br />
12.5f : constante float<br />
12UL :<br />
constante unsigned long int<br />
Applications :<br />
unsigned x = 120000UL*4/10000;<br />
long y = 15000L*4;<br />
F ou f<br />
float<br />
Float<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
17<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
18<br />
Organisation générale d’un module<br />
Déclarations<br />
…<br />
Fonction1<br />
…<br />
Fonction2<br />
…<br />
Définition d’une fonction<br />
! Déclaration :<br />
! du nom <strong>de</strong> la fonction,<br />
! du type <strong>de</strong> valeur r<strong>et</strong>ournée par la fonction<br />
! <strong>de</strong>s noms <strong>et</strong> <strong>de</strong>s types <strong>de</strong>s arguments transmis.<br />
! Corps <strong>de</strong> la fonction (entre accola<strong>de</strong>s) :<br />
! déclarations <strong>de</strong> données locales à la fonction<br />
! blocs d'instructions<br />
! r<strong>et</strong>our à la fonction appelante (avec un éventuel<br />
renvoi d'une valeur)<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
19<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
20<br />
5
Exemple<br />
Ancienne syntaxe<br />
double somme(double a, double b)<br />
{<br />
double res;<br />
res = a + b;<br />
r<strong>et</strong>urn res;<br />
}<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
21<br />
void init_glob( ( )<br />
{<br />
A=0;<br />
TOT=12E4;<br />
}<br />
double somme(a, b)<br />
double a, b;<br />
{<br />
double res;<br />
res = a + b;<br />
r<strong>et</strong>urn res;<br />
}<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
22<br />
double somme(double a, double b)<br />
{<br />
double res;<br />
res = a + b;<br />
r<strong>et</strong>urn res;<br />
}<br />
! ‘;’ omis en fin <strong>de</strong> ligne <strong>de</strong> définition<br />
! Paramètres transmis par valeur<br />
void init_glob()<br />
{<br />
A=0;<br />
TOT=12E4;<br />
}<br />
Fonction ne renvoie rien → void<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
23<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
24<br />
6
somme(int<br />
a, int b)<br />
{<br />
int s;<br />
s=a+b;<br />
r<strong>et</strong>urn s;<br />
}<br />
Type <strong>de</strong> la fonction est omis → int<br />
double pi(void<br />
void)<br />
{<br />
double x;<br />
x=atan<br />
atan(1.0)*4;<br />
r<strong>et</strong>urn x;<br />
}<br />
Fonction non déclarée → int<br />
Ici : inclure math.h<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
25<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
26<br />
Prototype<br />
! Perm<strong>et</strong> d'indiquer :<br />
! le type <strong>de</strong> donnée r<strong>et</strong>ourné par une fonction<br />
! le nombre <strong>et</strong> le type <strong>de</strong>s arguments transmis.<br />
# Déclaration <strong>de</strong> fonction.<br />
Exemples <strong>de</strong> prototype :<br />
double sin(double);<br />
double somme(double a, double b);<br />
Blocs d’instructions<br />
! Constitué :<br />
! d'une instruction élémentaire terminée par un<br />
caractère ";"<br />
ou<br />
! d'un ensemble d'instructions élémentaires encadrées<br />
par <strong>de</strong>s accola<strong>de</strong>s ; dans ce cas, le bloc d'instructions<br />
peut comporter <strong>de</strong>s déclarations (locales à ce bloc).<br />
ou<br />
! d'un simple caractère ';'.'<br />
'. Dans ce cas, l'instruction est<br />
vi<strong>de</strong> (sans eff<strong>et</strong>).<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
27<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
28<br />
7
x = 2*a + b;<br />
ou :<br />
{<br />
x = 2;<br />
y = 4;<br />
z = x+y;<br />
}<br />
ou :<br />
{<br />
int i;<br />
i = 3;<br />
x = 2*(i++);<br />
y=i;<br />
}<br />
Exemples<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
29<br />
Opérateur<br />
*<br />
/<br />
+<br />
-<br />
%<br />
^<br />
|<br />
&<br />
><br />
Opérateurs arithmétiques<br />
Description<br />
multiplication<br />
division<br />
addition<br />
soustraction<br />
modulo (reste <strong>de</strong> la division entière)<br />
ou exclusif (opération sur les bits)<br />
ou (opération sur les bits)<br />
<strong>et</strong> (opération sur les bits)<br />
décalage à gauche<br />
décalage à droite<br />
Exemple (a=5, b=3, c=1)<br />
x = 20*a x = 100<br />
z = 10.0/4 z = 2.5<br />
x = 3+b x = 6<br />
x = 3-b x = 0<br />
x = 8%a x = 3<br />
x = a^b x = 6<br />
x = a|b x = 7<br />
x = a&b x = 1<br />
x = ac x = 1<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
30<br />
Opérateurs logiques<br />
Opérateurs d’affectation<br />
Opérateur<br />
==<br />
||<br />
&&<br />
!=<br />
<<br />
><br />
=<br />
Description<br />
test d'égalité<br />
ou logique<br />
<strong>et</strong> logique<br />
différent<br />
inférieur<br />
supérieur<br />
inférieur ou égal<br />
supérieur ou égal<br />
Exemple (a=5, b=3)<br />
x = a==b x = 0<br />
x = (a==1)||(a==2) x = 0<br />
x = (a>0) && (a …<br />
Exemple (a=5, b=3, c=1)<br />
x = a<br />
⇒ x = 5<br />
a += 1<br />
⇒ a = 6<br />
a -= b<br />
⇒ a = 2<br />
a /= b-c<br />
⇒ a = 2<br />
a *= 8<br />
⇒ a = 40<br />
a %= b<br />
⇒ a = 2<br />
a ^= b<br />
⇒ a = 6<br />
a |= b<br />
⇒ a = 7<br />
a &= b<br />
⇒ a = 1<br />
a = b-2<br />
⇒ a = 2<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
31<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
32<br />
8
Écritures possibles<br />
Opérateur ternaire<br />
! x = (a=3)+1;<br />
m<strong>et</strong> 3 dans a <strong>et</strong> 4 dans x<br />
! x -= = (a+=10); augmente a <strong>de</strong> 10 <strong>et</strong> soustrait le résultat <strong>de</strong> x<br />
! x = y = 2;<br />
m<strong>et</strong> 2 dans y puis y dans x<br />
! x = a+=2;<br />
ajoute 2 à a, puis m<strong>et</strong> le résultat dans x<br />
Opérateur<br />
?:<br />
Description<br />
choix d'une valeur selon une<br />
condition<br />
si la condition est vraie, la<br />
première expression est<br />
r<strong>et</strong>ournée, sinon, la<br />
<strong>de</strong>uxième expression est<br />
r<strong>et</strong>ournée.<br />
Exemple (a=5, b=3, c=1)<br />
x=(a>4)?(b*2):(c+1) ⇒ x = 6<br />
x=(a3)<br />
x = a++<br />
x = ++a<br />
⇒ x = -5<br />
⇒ x = 5<br />
⇒ x = -6(0xFA)<br />
⇒ x = 0<br />
⇒ x = 5, a = 6<br />
⇒ x = 6, a = 6<br />
--<br />
auto décrémentation (post ou pré)<br />
x = a—<br />
x = --a<br />
⇒ x = 5, a = 4<br />
⇒ x = 4, a = 4<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
35<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
36<br />
9
Sizeof & Cast<br />
Expressions<br />
Opérateur<br />
sizeof<br />
(type)<br />
Description<br />
donne la taille d'un obj<strong>et</strong> (donnée ou type).<br />
est équivalent à une constante, déterminée par le compilateur.<br />
•sizeof(char) vaut 1<br />
•sizeof<br />
sur un tableau donne le nombre d'oct<strong>et</strong>s occupé par le<br />
tableau<br />
•sizeof(int)) vaut 2 si le type int est codé sur 16 bits<br />
opérateur cast (transtypage). Perm<strong>et</strong> <strong>de</strong> modifier le type d'une<br />
expression ; type représente un type <strong>de</strong> donnée prédéfini.<br />
Exemples :<br />
i = (int(<br />
int)(100.0*sin(2.45));<br />
x = (double)(2*a+1);<br />
! Utilisent <strong>de</strong>s opérateurs selon leur priorité<br />
Exemple :<br />
x = 2*a + 3*b/4/c; $<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
37<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
38<br />
Priorités<br />
Opérateurs<br />
Priorité<br />
() [] -> .<br />
15<br />
! ~ ++ -- + * - * * * & * (type) sizeof<br />
14<br />
* / %<br />
13<br />
+ -<br />
12<br />
><br />
11<br />
< >=<br />
10<br />
== !=<br />
9<br />
&<br />
8<br />
^<br />
7<br />
|<br />
6<br />
&&<br />
5<br />
||<br />
4<br />
?:<br />
3<br />
= += -= *= /= %= &= ^= |= =<br />
2<br />
,<br />
1<br />
(*) : Opérateurs unaires & pointeurs<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
39<br />
Structures conditionnelles<br />
Tests si … sinon …<br />
if (condition)<br />
bloc d'instructions à exécuter si la condition est vraie<br />
else<br />
bloc d'instructions à exécuter si la condition est fausse<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
40<br />
10
Structure itérative tant que<br />
Structure itérative faire … tant que<br />
Boucles tant que … faire :<br />
Boucles faire … tant que :<br />
while (condition)<br />
bloc d'instructions à exécuter si la condition est vraie.<br />
Exemple :<br />
while(x
Exemple :<br />
do<br />
{<br />
k = g<strong>et</strong>char( ( ); /* Acquisition clavier -> > k */<br />
switch (k) /* Test <strong>de</strong> k */<br />
{<br />
case '1':<br />
menu1( ); /* Appeler menu1 si '1' tapé */<br />
break;<br />
/* Quitter switch */<br />
case '2':<br />
menu2( ); /* Appeler menu1 si '2' tapé */<br />
break;<br />
/* Quitter switch */<br />
case 'q':<br />
case 'Q':<br />
printf("Fin du programme.\n");<br />
/* Quitter le programme si */<br />
exit(0); /* 'q' ou 'Q' tapé */<br />
<strong>de</strong>fault:<br />
printf("?????<br />
("?????\n");<br />
/* Erreur */<br />
}<br />
}<br />
while((k=='1') || (k=='2'));<br />
Rupture <strong>de</strong> séquence break<br />
Sortir d'une boucle :<br />
! while …<br />
! do … while<br />
! for<br />
! switch … case<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
45<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
46<br />
Rupture <strong>de</strong> séquence continue<br />
Interrompre le déroulement d'une boucle<br />
! while …<br />
! do … while<br />
! for<br />
→ directement à la fin du bloc d'instructions<br />
Exemple<br />
for(i=0; i
Branchements inconditionnels<br />
Jamais utilisés<br />
Portée <strong>de</strong>s données<br />
Exemple :<br />
...<br />
x = 3+i;<br />
if (x
Donnée locale à une fonction<br />
void fonction(int<br />
int a, double x) a <strong>et</strong> x sont <strong>de</strong>s variables locales à la fonction<br />
{<br />
unsigned c,d;<br />
...<br />
}<br />
c <strong>et</strong> d sont <strong>de</strong>s variables locales à la fonction<br />
Donnée locale à un bloc<br />
d’instructions<br />
void fonction(int<br />
int a, double x) a <strong>et</strong> x sont <strong>de</strong>s variables locales à la fonction<br />
{<br />
unsigned i; i est locale à la fonction<br />
...<br />
for(i=0; i
Exemple<br />
Allocation dynamique<br />
Exemple :<br />
void fonction(void<br />
void)<br />
{<br />
static x; x est <strong>de</strong> type int ; vaut 0 au démarrage du programme.<br />
static long double pi=3.14L;<br />
pi vaut 3.14 au démarrage du programme<br />
if(x
Données volatiles<br />
volatile<br />
Donnée dont le contenu est susceptible d’être modifié<br />
« tout seul ».<br />
⇒ Pas d’optimisation.<br />
Exemple :<br />
...<br />
volatile char x;<br />
extern volatile unsigned char pio;<br />
...<br />
Pointeurs<br />
Accès aux données à partir <strong>de</strong> leur adresse<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
61<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
62<br />
Notation :<br />
où<br />
<strong>et</strong><br />
nom_var<br />
*nom_var<br />
*nom_var<br />
Déclaration :<br />
nom_type *nom_var;<br />
Exemple :<br />
char *c;<br />
Déclaration<br />
représente la variable pointeur (qui contient une adresse)<br />
représente la variable pointée.<br />
c contient l'adresse <strong>de</strong> la variable pointée<br />
la variable pointée est <strong>de</strong> type char<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
63<br />
Pointeurs <strong>et</strong> constantes<br />
pointeur sur une chaîne <strong>de</strong> caractères constante :<br />
"chaîne <strong>de</strong> caractères"<br />
pointeur sur une donnée constante :<br />
const char *c; (*c est constant)<br />
pointeur constant :<br />
double * const v; (v est constant)<br />
pointeur constant sur une donnée constante :<br />
const int * const p; (p <strong>et</strong> *p sont constants)<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
64<br />
16
Arithmétique <strong>de</strong>s pointeurs<br />
Pointeurs <strong>et</strong> tableaux<br />
Opérations vali<strong>de</strong>s<br />
pointeur<br />
pointeur<br />
pointeur<br />
pointeur<br />
Opérateur<br />
+<br />
-<br />
-<br />
comparaison<br />
entier<br />
entier<br />
pointeur<br />
pointeur<br />
Résultat<br />
Pointeur<br />
Entier<br />
…<br />
p+i accès au<br />
p pointeur<br />
i entier<br />
élément situé à partir <strong>de</strong> p<br />
accès au i ème élément situé à partir <strong>de</strong><br />
⇒ fonctionnement i<strong>de</strong>ntique aux tableaux<br />
p-2<br />
p-1<br />
p p+1 p+2 …<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
65<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
66<br />
Parcours d’une chaîne <strong>de</strong> caractères<br />
char *p, c;<br />
p = "HELLO";<br />
c = *p; ⇒ c = 'H'<br />
c = *(p+1);<br />
p += 4;<br />
p--; ⇒ *p = 'L'<br />
⇒ c = 'E'<br />
⇒ *p = 'O'<br />
Types <strong>de</strong>s données pointées<br />
Pointeur ± entier ⇒ Valeur du pointeur ± n fois la taille <strong>de</strong> l'élément pointé.<br />
Exemple :<br />
char *pc ; pc pointe sur un caractère (taille : 1 oct<strong>et</strong>)<br />
int *pi ; pi pointe sur un entier (taille : 4 oct<strong>et</strong>s ici)<br />
....<br />
On suppose que pc=0x3AB0 <strong>et</strong> pi=0xE020<br />
pc+1 ; → vaut 0x3AB1<br />
pc+5 ; → vaut 0x3AB5<br />
pi+1 ; → vaut 0xE024<br />
pi+5 ; → vaut 0xE034<br />
⇒ nécessité <strong>de</strong> connaître le type <strong>de</strong> la donnée pointée<br />
l'arithmétique <strong>de</strong>s pointeurs ne fonctionne pas avec <strong>de</strong>s pointeurs void<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
67<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
68<br />
17
Utilité <strong>de</strong>s pointeurs<br />
! accé<strong>de</strong>r aux éléments d'un tableau<br />
! manipuler les chaînes <strong>de</strong> caractères<br />
! perm<strong>et</strong>tre aux fonctions <strong>de</strong> r<strong>et</strong>ourner plusieurs<br />
valeurs<br />
Tableaux<br />
Données <strong>de</strong> même type disposées <strong>de</strong> manière contiguë en<br />
mémoire.<br />
Exemple :<br />
double v[5];<br />
→ place 5 variables en virgule flottante à partir <strong>de</strong><br />
l'adresse v.<br />
! v est un pointeur constant → adresse <strong>de</strong> la première donnée<br />
du tableau.<br />
! v[i] perm<strong>et</strong> d’accé<strong>de</strong>r au i ème élément du tableau (i entier).<br />
! Le premier élément d'un tableau est toujours d’indice 0.<br />
Exemple : v[0] à v[4].<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
69<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
70<br />
Accès aux éléments <strong>de</strong>s tableaux<br />
v pointeur ⇒ accès à l'élément i du tableau :<br />
*(v+i).<br />
⇒ Les notations v[i] <strong>et</strong> *(v+i) sont équivalentes<br />
Elles peuvent être utilisées même lorsque v n'est pas un<br />
tableau<br />
Sizeof <strong>et</strong> tableaux<br />
sizeof appliqué sur un tableau<br />
⇒ espace mémoire occupé par le tableau.<br />
Exemple :<br />
double v[5] → sizeof(v) vaut 40<br />
(si le type double a une taille <strong>de</strong> 8)<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
71<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
72<br />
18
Sizeof <strong>et</strong> pointeurs<br />
sizeof(v)/<br />
(v)/sizeof(*v)<br />
indique le nombre d'éléments que peut contenir un tableau.<br />
!!! % sizeof appliqué à un pointeur donne<br />
la taille du pointeur.<br />
Exemple :<br />
char *str*<br />
= "Hello"; ⇒ sizeof(str<br />
str) ) donne 2<br />
(si pointeurs sur 2 oct<strong>et</strong>s)<br />
char str[10] = "Hello"; ⇒ sizeof(str<br />
str) ) donne 10<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
73<br />
Chaînes <strong>de</strong> caractères<br />
Chaînes <strong>de</strong> caractères<br />
→ tableaux <strong>de</strong> caractères.<br />
→ '\0' est le délimiteur <strong>de</strong> chaîne.<br />
notée entre guillem<strong>et</strong>s.<br />
Exemple : "Bonjour à tous"<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
74<br />
Fonctions <strong>et</strong> pointeurs<br />
<strong>Langage</strong> C ⇒ Transmission <strong>de</strong>s paramètres par valeurs.<br />
Transmission par référence → utilisation <strong>de</strong> pointeurs<br />
Exemple 1<br />
Fonction initialisant un tableau à 0 :<br />
void InitTab(int<br />
int *baseTab, unsigned nb)<br />
{<br />
unsigned i;<br />
for(i=0; i
Exemple 2<br />
Autre écriture possible <strong>de</strong> InitTab :<br />
void InitTab(int<br />
int *baseTab, unsigned nb)<br />
{<br />
while(nb<br />
(nb--)) *(baseTab<br />
baseTab++)=0;<br />
}<br />
Exemple 3<br />
Recherche <strong>de</strong> minimum <strong>et</strong> maximum :<br />
void MinMax(double x, double *Min, double *Max)<br />
{<br />
if(x < *Min) *Min*<br />
= x;<br />
else if(x > *Max) *Max*<br />
= x;<br />
}<br />
...<br />
double tab[100];<br />
unsigned i;<br />
double mini, maxi;<br />
...<br />
mini = maxi = *tab;<br />
for(i=1; i
Opérations sur les flux<br />
! « Ouverture »<br />
→ création du buffer<br />
→ création du lien avec le dispositif physique (FILE *)<br />
→ FILE* fopen(char *NomFichier*<br />
NomFichier, , char *Mo<strong>de</strong>)<br />
! Opérations d’entrées/sorties<br />
→ Entrées/sorties séquentielles<br />
→ Opérations binaires ou formatées<br />
→ Gestion du flux (positionnement, mise à jour buffer…)<br />
Utilisation <strong>de</strong>s flux<br />
Nécessite l’utilisation <strong>de</strong> <br />
Remarque :<br />
Opérations sur les flux peuvent échouer (disque plein, fichier<br />
introuvable…)<br />
→ Nécessiter <strong>de</strong> vérifier validité opérations<br />
→ Tester les co<strong>de</strong>s d’erreurs (EOF ou NULL).<br />
! « Ferm<strong>et</strong>ure »<br />
→ mise à jour <strong>de</strong>s données contenues dans le buffer<br />
→ <strong>de</strong>struction du buffer<br />
→ int fclose(FILE *f)<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
81<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
82<br />
Flux en sortie<br />
Flux en entrée<br />
! Accès en écriture <strong>de</strong>s fichiers.<br />
! Par défaut l’écran (stdout(<br />
tdout) → ne nécessite pas d’ouverture.<br />
! Fonctions <strong>de</strong> gestion du flux :<br />
! printf, fprintf, sprintf,…<br />
int printf(const<br />
char *format, …)<br />
int fprintf(FILE *f, const char *format, …)<br />
int sprintf(char *str*<br />
str, const char *format, …)<br />
! putchar, putc, fputc<br />
int putchar(int<br />
x)<br />
int putc(int<br />
x, FILE *f)<br />
int fputc(int<br />
x, FILE *f)<br />
! puts, fputs<br />
char *puts(const char *str)<br />
char *fputs(const char *str, FILE *f)<br />
! fwrite<br />
int fwrite(const<br />
void *buffer, size_t size, size_t nb, , FILE *f)<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
83<br />
! Accès en lecture <strong>de</strong>s fichiers.<br />
! Par défaut le clavier (stdin(<br />
stdin) → ne nécessite pas d’ouverture.<br />
! Fonctions <strong>de</strong> gestion du flux :<br />
! scanf, fscanf, sscanf,…<br />
int scanf(const<br />
const char *format,…)<br />
int fscanf(FILE *f, const char *format,…)<br />
int sscanf(char *s, const char *format,…)<br />
! g<strong>et</strong>char, g<strong>et</strong>c, fg<strong>et</strong>c<br />
int g<strong>et</strong>char(void<br />
void)<br />
int g<strong>et</strong>c(FILE *f)<br />
int fg<strong>et</strong>c(FILE *f)<br />
! g<strong>et</strong>s, fg<strong>et</strong>s<br />
char *g<strong>et</strong>s(void)<br />
char *fg<strong>et</strong>s(char *<strong>de</strong>st, size_t nb_max, FILE *f)<br />
! fread<br />
int fread(void<br />
*buffer, size_t size, size_t nb, , FILE *f)<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
84<br />
21
Gestion <strong>de</strong>s flux<br />
! long ftell(FILE *f)<br />
! int fseek(FILE *f, long offs<strong>et</strong>, int fromwhere)<br />
! void rewind(FILE *f)<br />
! int feof(FILE *f)<br />
! int fflush(FILE *f)<br />
Entrées sorties formatées<br />
Spécifications <strong>de</strong> format (pour printf <strong>et</strong> scanf) ) :<br />
% [flags[<br />
flags] ] [width[<br />
width] ] [.prec<br />
prec] ] [F|N|h|l] type<br />
Type Format <strong>de</strong> la sortie<br />
d : entier décimal signé<br />
i : entier décimal signé<br />
o : entier octal non signé<br />
u : entier décimal non signé<br />
x : avec printf = entier hexadécimal non signé en minuscules<br />
: avec scanf = entier hexadécimal<br />
X : avec printf = entier hexadécimal non signé en majuscules<br />
: avec scanf = entier hexadécimal long<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
85<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
86<br />
Spécifications <strong>de</strong> format (pour printf <strong>et</strong> scanf) ) :<br />
% [flags[<br />
flags] ] [width[<br />
width] ] [.prec<br />
prec] ] [F|N|h|l] type<br />
Type Format <strong>de</strong> la sortie<br />
f : virgule flottante [-]dddd.ddd[<br />
e : virgule flottante avec exposant [-]d.ddd[<br />
e [+/-]ddd<br />
g : format e ou f suivant la précision<br />
E : comme e mais l'exposant est la l<strong>et</strong>tre E<br />
G : comme g mais l'exposant est la l<strong>et</strong>tre E<br />
c : caractère simple<br />
s : affiche les caractères jusqu'au caractère nul ou jusqu'à ce que e la précision soit<br />
atteinte<br />
% : caractère <strong>de</strong> pourcentage %<br />
p : pointeur<br />
n : range (à l'adresse pointée par l'argument d'entrée) le nombre <strong>de</strong> caractères<br />
écrits.<br />
Spécifications <strong>de</strong> format (pour printf <strong>et</strong> scanf) ) :<br />
% [flags[<br />
flags] ] [width[<br />
width] ] [.prec<br />
prec] ] [F|N|h|l] type<br />
[flags] Signification<br />
aucun<br />
: résultat justifié à droite <strong>et</strong> complété à gauche par <strong>de</strong>s espaces s ou <strong>de</strong>s 0<br />
- : résultat justifié à gauche <strong>et</strong> complété à droite par <strong>de</strong>s espaces<br />
+ : les résultats commencent toujours par le signe + ou -<br />
espace<br />
: n'affiche le signe que pour les valeurs négatives<br />
# l'argument doit être converti en utilisant une autre forme :<br />
c,s,d,i,u<br />
: sans eff<strong>et</strong><br />
o : 0 sera placé <strong>de</strong>vant l'argument s'il est non nul<br />
x ou X<br />
: 0x ou 0X placé <strong>de</strong>vant la valeur <strong>de</strong> l'argument<br />
e, E, f : le résultat contiendra toujours un point décimal<br />
g or G<br />
: même chose mais sans les zéros à droite<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
87<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
88<br />
22
Spécifications <strong>de</strong> format (pour printf <strong>et</strong> scanf) ) :<br />
% [flags[<br />
flags] ] [width[<br />
width] ] [.prec<br />
prec] ] [F|N|h|l] type<br />
[width] Eff<strong>et</strong> sur l'affichage<br />
n : affichage d'au moins n caractères, au besoin complété par<br />
<strong>de</strong>s espaces<br />
0n<br />
: affichage d'au moins n caractères, au besoin complété à<br />
gauche par <strong>de</strong>s chiffres 0<br />
* : l'argument suivant <strong>de</strong> la liste contient la spécification <strong>de</strong><br />
largeur<br />
Spécifications <strong>de</strong> format (pour printf <strong>et</strong> scanf) ) :<br />
% [flags[<br />
flags] ] [width[<br />
width] ] [.prec<br />
prec] ] [F|N|h|l] type<br />
[.prec<br />
prec] Eff<strong>et</strong> sur l'affichage<br />
aucun<br />
: précision par défaut<br />
.0 : avec d,i,o,u,x précision par défaut<br />
: avec e, E, f pas <strong>de</strong> point décimal<br />
.n : n caractères au plus<br />
* : l'argument suivant <strong>de</strong> la liste contient la précision<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
89<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
90<br />
Spécifications <strong>de</strong> format (pour printf <strong>et</strong> scanf) ) :<br />
% [flags[<br />
flags] ] [width[<br />
width] ] [.prec<br />
prec] ] [F|N|h|l[<br />
F|N|h|l] ] type<br />
Modificateur Comment arg est interprété<br />
F : arg est interprété comme un pointeur long<br />
N : arg est interprété comme un pointeur court<br />
h : arg est interprété comme un entier <strong>de</strong> type short pour<br />
d,i,o,u,x,X<br />
l : arg est interprété comme un entier <strong>de</strong> type long pour<br />
d,i,o,u,x,X<br />
l : arg est interprété comme un réel <strong>de</strong> type double pour<br />
e,E,f,g,G (scanf(<br />
scanf)<br />
L : arg est interprété comme un réel <strong>de</strong> type long double<br />
pour e,E,f,g,G<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
91<br />
Copie <strong>de</strong> fichier texte<br />
#inclu<strong>de</strong><br />
<br />
#inclu<strong>de</strong><br />
<br />
#inclu<strong>de</strong><br />
<br />
void erreur(int<br />
err, const char *fmt*<br />
fmt, , ...)<br />
{<br />
va_list arg;<br />
va_start(arg<br />
arg,fmt);<br />
fprintf(st<strong>de</strong>rr<br />
st<strong>de</strong>rr,"Erreur [%d] : ",err<br />
err);<br />
vfprintf(st<strong>de</strong>rr<br />
st<strong>de</strong>rr,fmt,arg);<br />
va_end(arg<br />
arg);<br />
exit(err<br />
err);<br />
}<br />
main(int<br />
int argc, , char *argv*<br />
argv[])<br />
{<br />
FILE *fs*<br />
fs, , *fd*<br />
;<br />
int x ;<br />
if(argc<br />
argc>1)<br />
{<br />
fs=fopen<br />
fopen(argv[1],"r");<br />
if(fs<br />
fs==NULL)<br />
erreur(1,"Le fichier %s ne peut être<br />
ouvert.\n",<br />
n",argv[1]);<br />
}<br />
else fs=stdin<br />
stdin;<br />
if(argc<br />
argc>2)<br />
{<br />
fd=fopen<br />
fopen(argv[2],"w");<br />
if(fd<br />
fd==NULL)<br />
erreur(2,"Création <strong>de</strong> %s<br />
impossible.\n",<br />
n",argv[1]);<br />
}<br />
else fd=stdout<br />
stdout;<br />
while((x=<br />
((x=g<strong>et</strong>c(fs))!=EOF)<br />
if(putc<br />
putc(x, (x,fd)==EOF) erreur(3,"Erreur<br />
en écriture");<br />
fclose(fd<br />
fd);<br />
fclose(fs<br />
fs);<br />
r<strong>et</strong>urn 0;<br />
}<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
92<br />
23
Fonctions standard<br />
Manipulation <strong>de</strong> chaînes <strong>de</strong><br />
caractères <br />
memchr<br />
strcat<br />
strchr<br />
strrstr<br />
Définies par le C<br />
memcmp<br />
memcpy<br />
strncat<br />
strcpy<br />
strrchr<br />
strspn<br />
strlen<br />
strerror<br />
memmove<br />
strncpy<br />
strcspn<br />
mems<strong>et</strong><br />
strcmp<br />
strpbrk<br />
strncmp<br />
strtok<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
93<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
94<br />
Entrées sorties <br />
clearerr<br />
fclose<br />
fcloseall<br />
fdopen<br />
feof<br />
ferror<br />
fflush<br />
fg<strong>et</strong>c<br />
fg<strong>et</strong>char<br />
fg<strong>et</strong>pos<br />
fg<strong>et</strong>s<br />
fileno<br />
ftell<br />
g<strong>et</strong>c<br />
g<strong>et</strong>char<br />
g<strong>et</strong>s<br />
g<strong>et</strong>w<br />
perror<br />
printf<br />
putcs<br />
putchar<br />
puts<br />
tmpfile<br />
tmpnam<br />
ung<strong>et</strong>c<br />
unlink<br />
fwrite<br />
flushall<br />
fopen<br />
fprintf<br />
fputc<br />
fputchar<br />
fputs<br />
fread<br />
freopen<br />
fscanf<br />
fseek<br />
fs<strong>et</strong>pos<br />
putw<br />
remove<br />
vfprintf<br />
rewind<br />
scanf<br />
s<strong>et</strong>buf<br />
s<strong>et</strong>vbuf<br />
sprintf<br />
scanf<br />
_strerror<br />
strerror<br />
vfscanf<br />
vprintf<br />
vscanf<br />
vsprintf<br />
vsscanf<br />
rename<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
95<br />
Fonctions utilitaires <br />
atof<br />
atoi<br />
atol<br />
strtod<br />
strtol<br />
strtoul<br />
rand<br />
srand<br />
bsearch<br />
qsort<br />
calloc<br />
malloc<br />
realloc<br />
free<br />
abort<br />
exit<br />
atexit<br />
system<br />
g<strong>et</strong>env<br />
abs<br />
labs<br />
ldiv<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
96<br />
div<br />
24
Structures<br />
→ Agglomérats <strong>de</strong> données<br />
! Exemple :<br />
! Un individu :<br />
! Nom – Age – Profession – Poids<br />
& Ensemble <strong>de</strong> données propres à chaque individu<br />
& Informations rangées dans une variable unique (pour<br />
chaque individu)<br />
→ Champs <strong>de</strong> la structure<br />
Déclaration <strong>de</strong>s structures<br />
Déclaration :<br />
struct [TypeStructure]<br />
{<br />
TypeVar1 var1;<br />
TypeVar2 var2;<br />
…<br />
} [NomStruct1][,NomStruct2][,…] ;<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
97<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
98<br />
Utilisation <strong>de</strong>s structures<br />
Exemple <strong>de</strong> déclaration :<br />
struct TIndividu<br />
{<br />
char Nom[40];<br />
unsigned age;<br />
char Profession[80];<br />
float Poids;<br />
};<br />
struct TIndividu Marcel, Maurice;<br />
Utilisation :<br />
Chaque champ <strong>de</strong> la structure est utilisable comme une<br />
variable ordinaire (<strong>de</strong> type défini lors <strong>de</strong> la<br />
déclaration <strong>de</strong> la structure).<br />
On utilise la notation :<br />
.<br />
Exemples :<br />
scanf("%s",<br />
("%s",Marcel.Nom);<br />
Maurice.Age=32;<br />
Marcel.Poids=58.6;<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
99<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
100<br />
25
Types <strong>de</strong> données contenues<br />
Les données contenues dans une structure sont<br />
toutes celles autorisées par le langage C :<br />
! Types <strong>de</strong> base,…<br />
! Types utilisateurs<br />
! Structures<br />
! Tableaux<br />
! Pointeurs<br />
! …<br />
Exemple<br />
Exemple :<br />
struct<br />
{<br />
int ac;<br />
double t[10];<br />
struct { int a, ab, ac[3]; } si;<br />
}tv, tbv[10];<br />
…<br />
tv.t[4]=5;<br />
tv.ac=3;<br />
tv.si.ac[2]=0;<br />
tbv[0].<br />
[0].si.ac[0]=1;<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
101<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
102<br />
Structures <strong>et</strong> pointeurs<br />
Structure : donnée à fort encombrement mémoire<br />
→ Éviter la transmission par valeur lors d’un d<br />
appel <strong>de</strong> fonction<br />
→ Utilisation <strong>de</strong> pointeurs<br />
Exemple :<br />
void AcqParam(struct<br />
TIndividu *x);<br />
…<br />
struct TIndividu Marcel, Maurice, Groupe[30];<br />
AcqParam(&Marcel);<br />
AcqParam(Groupe+2); ou AcqParam(&(Groupe[2]));<br />
Pointeurs <strong>de</strong> structures<br />
Si x est un pointeur <strong>de</strong> structure, on accè<strong>de</strong><br />
à la variable<br />
pointée e par la notation :<br />
(*x). ou<br />
x -> <br />
Exemple :<br />
void AcqParam(struct<br />
TIndividu *x)<br />
{<br />
scanf("%s",(*x).nom);<br />
ou scanf("%s",x<br />
("%s",x->nom);<br />
scanf("%u",&(x<br />
("%u",&(x->age));<br />
x->Poids=60.0;<br />
}<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
103<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
104<br />
26
Champs <strong>de</strong> bits<br />
→ Définition <strong>de</strong> données<br />
entières<br />
<strong>de</strong> p<strong>et</strong>ite taille (nombre <strong>de</strong><br />
bits indiqué)<br />
→ Utilisation : Indicateurs (flags(<br />
flags), programmation bas niveau<br />
Exemple :<br />
struct<br />
{<br />
unsigned CopyOnly:1;<br />
unsigned CaseDepend:1;<br />
unsigned Mo<strong>de</strong>:2;<br />
:4;<br />
int Rsv:8;<br />
}Options;<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
105<br />
Unions<br />
Déclaration & utilisation i<strong>de</strong>ntiques aux structures<br />
Mais<br />
Tous les champs sont situés à la même adresse<br />
Exemple : (pour examiner le codage d'un nombre<br />
double)<br />
union {<br />
double vd;<br />
unsigned char vb[sizeof<br />
sizeof(double)];<br />
}x;<br />
…<br />
x.vd = 0.25;<br />
for(i=0; i
La comman<strong>de</strong> inclu<strong>de</strong><br />
→ perm<strong>et</strong> d’insérer le fichier texte spécifié, à l’endroit où la<br />
comman<strong>de</strong> apparaît<br />
! Syntaxe :<br />
! #inclu<strong>de</strong><br />
"nom_<strong>de</strong>_fichier"<br />
ou<br />
! #inclu<strong>de</strong><br />
<br />
→ Souvent utilisé pour charger les fichiers d’en-tête (hea<strong>de</strong>rs, .h)<br />
Exemples :<br />
#inclu<strong>de</strong><br />
<br />
#inclu<strong>de</strong> <br />
→ fichiers livrés avec le compilateur<br />
→ contiennent <strong>de</strong>s définitions standard compatibles avec les bibliothèques<br />
→ ne pas les modifier !!!<br />
Recherche le fichier dans le<br />
répertoire pris par défaut pour le<br />
compilateur<br />
Recherche le fichier dans le répertoire<br />
courant, puis, s’il n’a pas été trouvé,<br />
dans le répertoire pris par défaut<br />
pour le compilateur<br />
Contenu :<br />
• déclarations <strong>de</strong> fonctions (prototypes)<br />
• définition <strong>de</strong> données externes (Exemple errno)<br />
• définition <strong>de</strong> constantes prédéfinies (Exemple : M_PI)<br />
• macro-définitions<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
109<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
110<br />
La comman<strong>de</strong> <strong>de</strong>fine<br />
Constantes prédéfinies<br />
perm<strong>et</strong> <strong>de</strong> définir :<br />
<strong>de</strong>s constantes<br />
ou<br />
<strong>de</strong>s macros<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
111<br />
#<strong>de</strong>fine<br />
Nom_Symbole Expression<br />
→ substitue par la suite dans le source toutes les occurrences <strong>de</strong><br />
Nom_Symbole par l’expression<br />
(remplacement intégral <strong>de</strong> texte)<br />
Exemple :<br />
#<strong>de</strong>fine<br />
M_PI 3.14159265<br />
#<strong>de</strong>fine<br />
PI2 (M_PI*2.0)<br />
Par la suite, si dans un programme on utilise l’instruction suivante<br />
:<br />
x = PI2*r ;<br />
le préprocesseur remplace la ligne par :<br />
x = (3.14159265*2.0)*r;<br />
→ utilisation efficace <strong>de</strong> constantes<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
112<br />
28
Macros<br />
Définition <strong>de</strong> macros<br />
→ s’apparentent visuellement à <strong>de</strong>s fonctions, mais<br />
fonctionnement plus efficace<br />
→ fonctionnent par substitution <strong>de</strong> texte<br />
Exemple :<br />
#<strong>de</strong>fine<br />
MEAN(a,b) (a+b)/2<br />
à l’utilisation, on écrit : z = MEAN(x,2-i);<br />
le préprocesseur remplace la ligne par : z = (x+2-i)/2<br />
;<br />
→ les arguments ont été remplacés par substitution <strong>de</strong> texte<br />
→ la macro MEAN( ) a été remplacée par substitution <strong>de</strong> texte<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
113<br />
!! ATTENTION !!<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
114<br />
Exemple<br />
#<strong>de</strong>fine<br />
PRODUIT(u,v) u*v<br />
à l’utilisation : z = PRODUIT(3+2,5) ;<br />
donnera : z = 3+2*5 ; (13 au lieu <strong>de</strong> 25 ! )<br />
→ Utiliser <strong>de</strong>s parenthèses !<br />
Exemples :<br />
#<strong>de</strong>fine<br />
PRODUIT(u,v)<br />
u * v<br />
#<strong>de</strong>fine<br />
Mini(a,b) a < b ? a : b<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
115<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
116<br />
29
Exemples :<br />
#<strong>de</strong>fine<br />
PRODUIT(u,v) (u)*(v)<br />
Exemples :<br />
#<strong>de</strong>fine<br />
PRODUIT(u,v) (u)*(v)<br />
#<strong>de</strong>fine<br />
Mini(a,b)<br />
(a)
Les comman<strong>de</strong>s if, if<strong>de</strong>f, ifn<strong>de</strong>f, endif<br />
Exemple<br />
→ Compilation conditionnelle<br />
#if expression<br />
#else<br />
Source compilé dans le<br />
cas contraire<br />
#endif<br />
Source compilé si<br />
l’expression est vraie<br />
#if<strong>de</strong>f symbole<br />
#else<br />
Source compilé si le<br />
symbole est défini<br />
Source compilé dans le<br />
cas contraire<br />
#endif<br />
#ifn<strong>de</strong>f symbole<br />
#else<br />
Source compilé si le<br />
symbole n’est pas<br />
défini<br />
Source compilé dans le<br />
cas contraire<br />
#endif<br />
#if<strong>de</strong>f<br />
__TURBOC__<br />
#inclu<strong>de</strong><br />
<br />
#if MODEL== __SMALL__<br />
int *px<br />
;<br />
#else<br />
void *px<br />
;<br />
#endif<br />
#endif<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
121<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
122<br />
Transtypage<br />
Initialisation <strong>de</strong> données<br />
! cast<br />
→ Conversion <strong>de</strong> type explicite<br />
→ Perm<strong>et</strong> d'indiquer au compilateur le type à utiliser<br />
Exemples :<br />
x = (long)a * b/c;<br />
void CopyDat(void<br />
*d, void *s, size_t sz)<br />
{<br />
size_t i;<br />
for(i=0; i
o Classe static :<br />
o Donnée e initialisée e au chargement du programme<br />
(expression constante évaluée e par le compilateur)<br />
o La valeur peut changer au cours du programme<br />
o Pas <strong>de</strong> co<strong>de</strong> générég<br />
lors <strong>de</strong> la déclarationd<br />
Exemple :<br />
static int x=4;<br />
o Constantes :<br />
o I<strong>de</strong>m static, , avec valeur non modifiable<br />
o Exemple :<br />
void fonctionX(void)<br />
{<br />
char t1[ ]="toto est le plus beau";<br />
→ t1 est un tableau dynamique <strong>de</strong> 22 caractères<br />
→ la chaîne <strong>de</strong> caractères est recopiée à chaque appel<br />
<strong>de</strong> la fonction fonctionX<br />
→ le contenu <strong>de</strong> t1 est modifiable<br />
}<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
125<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
126<br />
! Initialisation <strong>de</strong> données<br />
o Exemple :<br />
void fonctionY(void)<br />
{<br />
static char t1[ ]="toto est le plus beau";<br />
→ t1 est un tableau statique <strong>de</strong> 22 caractères<br />
→ la chaîne <strong>de</strong> caractères est chargée au démarrage<br />
du programme<br />
→ le contenu <strong>de</strong> t1 est modifiable<br />
}<br />
! Initialisation <strong>de</strong> données<br />
o Exemple :<br />
void fonctionZ(void)<br />
{<br />
const char t1[ ]="toto est le plus beau";<br />
→ t1 est un tableau constant <strong>de</strong> 22 caractères<br />
→ la chaîne <strong>de</strong> caractères est chargée au démarrage<br />
du programme<br />
→ le contenu <strong>de</strong> t1 n'est pas modifiable<br />
}<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
127<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
128<br />
32
! Initialisation <strong>de</strong> données<br />
o Exemple :<br />
void fonctionW(void)<br />
{<br />
char *t1="toto est le plus beau";<br />
→ t1 est un pointeur initialisé sur une chaîne <strong>de</strong><br />
caractères constante (à chaque appel <strong>de</strong> fonctionW)<br />
}<br />
! Initialisation <strong>de</strong> données<br />
o Exemple :<br />
void fonctionY(void)<br />
{<br />
static char *t1="toto est le plus beau";<br />
→ t1 est un pointeur initialisé au chargement du<br />
programme sur une chaîne <strong>de</strong> caractères constante<br />
chaîne)<br />
}<br />
→ t1 pourra être modifié (pour pointer sur une autre<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
129<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
130<br />
Fonction main<br />
! Initialisation <strong>de</strong> données<br />
o Exemple :<br />
double tab[ ]={1.0, 3.0, 5.0, 7.0};<br />
char *mots[ ]={"toto","titi","tata",0};<br />
struct {<br />
char *nom;<br />
double val;<br />
} liste[100] = {<br />
{ "pi", 3.14 },<br />
{ "x", 200.12 },<br />
};<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
131<br />
! Démarrage du programme<br />
! Renvoie une valeur entière au système d'exploitation<br />
→ co<strong>de</strong> d'erreur<br />
! Adm<strong>et</strong> 3 paramètres :<br />
int main(int<br />
int argc, , char *argv*<br />
argv[ [ ], char *arge*<br />
arge[ [ ])<br />
! Paramètres "transmis" par le système d'exploitation<br />
! argc : nombre <strong>de</strong> paramètres sur la ligne <strong>de</strong> comman<strong>de</strong> (à l'invocation<br />
du programme)<br />
! argv : chaînes <strong>de</strong> caractères contenant les paramètres<br />
! arge : variables d'environnement<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
132<br />
33
Exemple<br />
pgm.exe –x3<br />
toto.dat titi.out<br />
• argc = 4<br />
• argv[0]="<br />
[0]="pgm.exe"" (avec le chemin d'accès compl<strong>et</strong>)<br />
• argv[1]="<br />
[1]="-x3"<br />
• argv[2]="<br />
[2]="toto.dat"<br />
• argv[3]="<br />
[3]="titi.out"<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
133<br />
Pointeurs <strong>de</strong> fonctions<br />
Nom <strong>de</strong> fonction → adresse <strong>de</strong> la fonction<br />
→ Pointeur <strong>de</strong> fonction<br />
Peut être utilisé pour in<strong>de</strong>xer une fonction parmi plusieurs.<br />
Exemple :<br />
void TriBulle(int<br />
int t[ ], int nb);<br />
void TriInsertion(int<br />
int t[ ], int nb);<br />
void (*fctTri<br />
fctTri)( )(int<br />
t[ ], int nb);<br />
…<br />
int tab[ ] = {1, 4, 0, -1, 2};<br />
fctTri = TriBulle;<br />
fctTri(tab,<br />
(tab,sizeof(tab)/sizeof(*tab));<br />
fctTri = TriInsertion;<br />
fctTri(tab,<br />
(tab,sizeof(tab)/sizeof(*tab));<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
134<br />
Allocation dynamique <strong>de</strong> mémoire<br />
→ Quand un espace mémoire m moire est requis, <strong>de</strong> taille<br />
inconnue lors <strong>de</strong> la conception du programme<br />
→ Pour optimiser l'utilisation <strong>de</strong> la mémoirem<br />
moire<br />
→ Deman<strong>de</strong> <strong>de</strong> mémoire m moire à l'environnement<br />
Fonctions :<br />
• void * malloc(size_t<br />
sz);<br />
Renvoie un pointeur sur la zone allouée<br />
ou NULL si pas d'espace disponible<br />
• void free(void<br />
* ptr);<br />
Libère l'espace mémoire m moire attribué par malloc<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
135<br />
Exemple<br />
int nb, , *tab;<br />
printf("Nombre <strong>de</strong> valeurs à acquérir :");<br />
scanf("%d",&<br />
("%d",&nb);<br />
tab = malloc(nb<br />
nb*sizeof(*tab));<br />
if(tab!=NULL) {<br />
int i;<br />
for(i=0; i
Fonctions à liste <strong>de</strong> paramètres<br />
variable<br />
! En C, on peut définir <strong>de</strong>s fonctions avec un<br />
nombre <strong>de</strong> paramètres inconnu :<br />
Exemples :<br />
void FctErr(int<br />
err, , …);<br />
int printf(const<br />
char *format, …);<br />
! Nécessité d'avoir au moins un paramètre connu<br />
! Gestion par va_list, va_start, va_arg, va_end<br />
→ définis dans stdarg.h<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
137<br />
Exemple<br />
void ErrPrintf(int ext, const char *fmt, …)<br />
{<br />
va_list ap;<br />
printf(ext ? "Erreur : " : "Avertissement : ");<br />
va_start(ap,fmt);<br />
vprintf(fmt,ap);<br />
va_end(ap);<br />
if(ext) exit(ext);<br />
}<br />
…<br />
F = fopen(nf="toto.dat","r");<br />
if(F==NULL) ErrPrintf(1,"Le fichier '%s' ne peut être<br />
ouvert.\n",nf);<br />
…<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
138<br />
Signal<br />
! Gestion d'événements exceptionnels<br />
! Défini dans signal.h<br />
void (*signal(int<br />
int sig, void (*handler<br />
handler)( )(int)))(int);<br />
Détermine la façon dont les signaux ultérieurs seront traités.<br />
handler : fonction <strong>de</strong> traitement du signal<br />
Fonctions prédéfinies :<br />
SIG_DFL : comportement par défaut<br />
SIG_IGN : le signal sera ignoré<br />
R<strong>et</strong>our : handler ou SIG_ERR en cas d'erreur<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
139<br />
Signaux :<br />
<strong>Langage</strong> C<br />
SIGABRT : arrêt anormal<br />
SIGFPE<br />
: erreur arithmétique<br />
SIGILL<br />
SIGINT<br />
: instruction illégale<br />
: appel au système invali<strong>de</strong><br />
SIGSEGV : accès mémoire interdit<br />
SIGTERM : <strong>de</strong>man<strong>de</strong> d'arrêt du programme<br />
Quand signal survient :<br />
1. Le comportement par défaut est rétabli<br />
2. La fonction handler est appelée<br />
3. Si la fonction rend la main, le programme se poursuit à<br />
l'endroit où il avait été interrompu<br />
M. <strong>Deloizy</strong> <strong>Langage</strong> C<br />
140<br />
35
TD1 : TYPES DE DONNÉES – CODAGE<br />
I. Caractères.<br />
I.1. Indiquer les co<strong>de</strong>s ASCII <strong>de</strong>s caractères suivants :<br />
'A', 'B', 'q', '?','*', '0' (zéro), '8', '\r', '\n', '\t'<br />
I.2. La mémoire contient les données suivantes (hexadécimal) :<br />
adresses<br />
données<br />
2A3C 43 27 65 73 74 20 65 6E<br />
2A44 20 41 53 43 49 49 2E 00<br />
Indiquer pour chaque oct<strong>et</strong> le caractère correspondant.<br />
II. Entiers.<br />
On suppose ici que les poids faibles sont situés en adresse basse.<br />
II.1. Écrire en hexadécimal puis en binaire le contenu <strong>de</strong> la mémoire pour les valeurs suivantes (entiers sur 16 bits)<br />
: 1234, 37840, 65535, -128, -1<br />
II.2. Donner les résultats <strong>de</strong>s opérations suivantes :<br />
• pour <strong>de</strong>s entiers signés codés sur 16 bits<br />
• pour <strong>de</strong>s entiers non signés codés sur 16 bits<br />
• pour <strong>de</strong>s entiers signés codés sur 32 bits<br />
1000 - 1024<br />
25000 + 30535<br />
65536 - 1<br />
II.3. Calculer les résultats <strong>de</strong>s opérations suivantes (opérateurs du C) :<br />
M<strong>et</strong>tre le résultat en binaire, hexadécimal <strong>et</strong> décimal sur 8 bits.<br />
25 & 51<br />
25 | 51<br />
25 ^ 51<br />
~25<br />
-25<br />
III. Chaînes <strong>de</strong> caractères.<br />
Indiquer le contenu mémoire obtenu avec les chaînes <strong>de</strong> caractères suivantes, selon <strong>de</strong>ux codages possibles<br />
(nombre <strong>de</strong> caractères en tête ou zéro terminal) :<br />
"TOTO"<br />
"Il fait chaud\n"<br />
"02 + 20 = 22\n"<br />
IV. Virgule flottante.<br />
Étudier les résultats obtenus avec les nombres en virgule flottante codés sur 64 bits, selon la norme IEEE 754 :<br />
e<br />
x = ± m⋅2<br />
S E' F<br />
b 63 b 62 b 52 b 51 b 0<br />
• e : exposant<br />
• m : mantisse. 1.0 ≤ m < 2.0<br />
• S : signe. 1 bit. 0 : positif, 1 : négatif<br />
• E' = e+1023. 11 bits. 1 ≤ E' ≤ 2047<br />
• F = m-1. Partie fractionnaire <strong>de</strong> la mantisse. 52 bits.<br />
Représenter le contenu mémoire correspondant aux valeurs 1.0, 2.0 <strong>et</strong> 5.0.<br />
Quelle est la valeur positive la plus p<strong>et</strong>ite possible ?<br />
Quelle est la valeur positive la plus gran<strong>de</strong> possible ?<br />
Quel est le nombre <strong>de</strong> chiffres significatifs ?<br />
V. Tableaux<br />
Soit un tableau d'entiers codés sur 16 bits <strong>et</strong> contenant les valeurs : { 2, 4, 8, 16, 32 }<br />
Représenter le contenu <strong>de</strong> la mémoire correspondant à ce tableau.<br />
Quel est le nombre d'oct<strong>et</strong>s nécessaire au stockage du tableau ?
TD2 : PREMIERS PROGRAMMES<br />
I. Écrire un programme affichant « BONJOUR » à l’écran.<br />
II. Écrire un programme qui <strong>de</strong>man<strong>de</strong> le prénom <strong>de</strong> l’utilisateur ainsi que son année <strong>de</strong> naissance. Ensuite, le<br />
programme affichera un texte sous la forme suivante :<br />
Bonjour "xxxxx" (prénom).<br />
Ton année <strong>de</strong> naissance est dddd. (année <strong>de</strong> naissance)<br />
III.a. Écrire un programme qui affiche la table <strong>de</strong> multiplication par 5 sous la forme :<br />
5 x 1 = 5<br />
5 x 2 = 10<br />
5 x 3 = 15<br />
....<br />
5 x 9 = 45<br />
III.b. Modifier le programme précé<strong>de</strong>nt en créant une fonction mult à laquelle on transm<strong>et</strong> le numéro <strong>de</strong> la table à<br />
afficher :<br />
void mult(int table)<br />
Utiliser c<strong>et</strong>te fonction dans un programme qui <strong>de</strong>man<strong>de</strong> à l’utilisateur le numéro <strong>de</strong> la table qu’il souhaite<br />
visualiser. Le programme continuera tant que l’utilisateur entre une valeur strictement positive.<br />
TD3 : UTILISATION DE TABLEAUX.<br />
I. Écrire une fonction qui <strong>de</strong>man<strong>de</strong> à l’utilisateur <strong>de</strong> faire l’acquisition <strong>de</strong> n entiers sous la forme suivante :<br />
Nombre <strong>de</strong> valeurs :<br />
Valeur n° 1 :<br />
Valeur n° 2 :<br />
Valeur n° 3 :<br />
....<br />
Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
unsigned AcqTab(int tb[], unsigned NbMax);<br />
La fonction r<strong>et</strong>ourne le nombre <strong>de</strong> valeurs saisies<br />
tb est le tableau qui doit être chargé<br />
NbMax est le nombre maximal <strong>de</strong> valeurs que peut contenir tb<br />
II. Écrire une fonction qui compte le nombre <strong>de</strong> valeurs paires dans un tableau. Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
int nbpairs(int tab[], unsigned nbval);<br />
nbval indique le nombre d'éléments contenus dans le tableau. Pourquoi ce paramètre est-il indispensable ?<br />
III. Écrire une fonction qui remplit un tableau avec <strong>de</strong>s nombres ni pairs, ni multiples <strong>de</strong> 3, en commençant par 5.<br />
Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
void inittab(int tab[], unsigned nbval);<br />
IV. Écrire une fonction trouvant le minimum <strong>et</strong> le maximum dans un tableau. Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
void minmax(double *tab, unsigned nbval, double *min, double *max);<br />
V. Soient les valeurs suivantes stockées dans un tableau : { 2, -3, 1, 0, 5, 2 }<br />
V.1 Effectuer une rotation à gauche du tableau afin d'obtenir : { -3, 1, 0, 5, 2, 2 }. Afficher le résultat.<br />
V.2. Effectuer une rotation à droite du tableau initial afin d'obtenir : { 2,2,-3, 1, 0, 5 }
TD4 : CONVERSIONS ASCII / NUMÉRIQUES<br />
I. Écrire une fonction r<strong>et</strong>ournant un entier correspondant à la valeur numérique contenue dans une chaîne transmise<br />
en paramètre. Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
int AscToInt(const char *<strong>de</strong>cstr);<br />
C<strong>et</strong>te fonction pourra être utilisée par exemple <strong>de</strong> la manière suivante :<br />
...<br />
x = AscToInt("26789");<br />
...<br />
Dans ce cas, x prendra la valeur numérique 26789.<br />
a ⋅10<br />
+ b ⋅10<br />
+<br />
On rappelle qu'un nombre abc peut s'écrire : (( ) ) c<br />
II. Écrire une fonction équivalente à la précé<strong>de</strong>nte perm<strong>et</strong>tant <strong>de</strong> convertir un nombre écrit en binaire, dont le<br />
prototype sera :<br />
int AscBinToInt(const char *binstr);<br />
III. Faire <strong>de</strong> même pour un nombre écrit en hexadécimal.<br />
int AscHexToInt(const char *hexstr);<br />
IV. Que se passe-t-il si un caractère non prévu est contenu dans la chaîne ? Proposer un moyen <strong>de</strong> remédier à ce<br />
problème.<br />
TD5 : TRAITEMENTS SUR LES CHAÎNES<br />
I. Écrire une fonction comptant le nombre <strong>de</strong> caractères contenus dans une chaîne. Le prototype <strong>de</strong> c<strong>et</strong>te fonction<br />
sera :<br />
int strlen(const char *str);<br />
II.a. Écrire une fonction comptant le nombre <strong>de</strong> caractères i<strong>de</strong>ntiques x contenus dans une chaîne. Le prototype <strong>de</strong><br />
c<strong>et</strong>te fonction sera :<br />
int nbcar(char x, const char *str); /* recherche x dans str */<br />
II.b. Modifier la fonction précé<strong>de</strong>nte pour qu'elle ne différencie pas les minuscules <strong>et</strong> majuscules.<br />
III. Écrire une fonction perm<strong>et</strong>tant <strong>de</strong> comparer <strong>de</strong>ux chaînes <strong>de</strong> caractères. Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
int cmpstr(const char *str1, const char *str2);<br />
L'entier r<strong>et</strong>ourné sera positif si str2 est situé après str1 dans un classement alphabétique <strong>et</strong> 0 si les chaînes sont<br />
i<strong>de</strong>ntiques.<br />
IV. Écrire une fonction comptant le nombre <strong>de</strong> mots dans une phrase. Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
int nbmots(const char *str);<br />
Par exemple, si str contient " le p<strong>et</strong>it train passe dans l'alpage…\n " la fonction doit r<strong>et</strong>ourner la valeur 7.
TD6 : FICHIERS<br />
I. Écrire un programme affichant à l'écran les fichiers textes dont les noms seront transmis sur la ligne <strong>de</strong><br />
comman<strong>de</strong> lors <strong>de</strong> l'appel du programme.<br />
II. Écrire un programme affichant le contenu d'un fichier quelconque en hexadécimal <strong>et</strong> en ASCII, sous la forme<br />
suivante :<br />
0000 4D 5A 78 00 BC 00 00 00 A0 04 01 00 FF FF 00 00 MZx.............<br />
0010 00 00 00 00 00 01 00 00 1E 00 00 00 01 00 00 00 ................<br />
0020 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................<br />
0030 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................<br />
0040 F6 38 F6 38 46 52 41 01 00 52 03 4E 53 43 4F 00 .8.8FRA..R.NSCO.<br />
0050 03 06 00 16 00 1A 00 01 04 FF FF 48 03 02 00 56 ...........H...V<br />
0060 03 03 00 66 03 08 00 7D 03 02 01 FF FF 8C 03 03 ...f............<br />
0070 CC EA 03 9A 03 EB 03 D2 03 EC 03 FC 03 ED 03 14 ................<br />
0080 04 EE 03 33 04 EF 03 69 04 F0 03 8A 04 F1 03 AE ...3...i........<br />
0090 04 F2 03 C9 04 F3 03 00 05 F4 03 23 05 F5 03 57 ...........#...W<br />
00A0 05 F6 03 7A 05 F7 03 84 05 F8 03 B1 05 F9 03 DE ...z............<br />
00B0 05 FA 03 02 06 FB 03 17 06 FC 03 26 06 FD 03 35 ...........&...5<br />
III. Statistiques sur un fichier<br />
III.1. Écrire un programme qui compte les mots contenus dans un fichier texte.<br />
III.2. (optionnel) Modifier le programme pour indiquer (dans l'ordre <strong>de</strong> la fréquence d'apparition) les mots présents<br />
dans le fichier.
TP1 : DÉCLARATIONS, PREMIERS PROGRAMMES, DÉBOGUAGE<br />
I. Écrire un programme affichant "Bonjour".<br />
II. Soit le programme suivant :<br />
#inclu<strong>de</strong> <br />
/* Affichage <strong>de</strong> la table <strong>de</strong> multiplication par m */<br />
void mtable(int m, int nmax)<br />
{<br />
int i;<br />
for(i=1; i
TP2 : MANIPULATIONS DE CHAÎNES DE CARACTÈRES<br />
I. Saisie <strong>de</strong> chaînes<br />
Définir un tableau <strong>de</strong> 256 caractères.<br />
Faire la saisie d'une chaîne <strong>de</strong> caractères (limitée à 20 caractères) en utilisant :<br />
la fonction scanf<br />
la fonction g<strong>et</strong>s<br />
la fonction fg<strong>et</strong>s<br />
Dans chaque cas,<br />
Afficher normalement la chaîne saisie (en utilisant printf)<br />
Afficher en hexadécimal le co<strong>de</strong> ASCII <strong>de</strong>s 80 premiers oct<strong>et</strong>s du tableau. (On pourra concevoir une fonction qui<br />
affiche en hexadécimal le contenu d'un tableau <strong>de</strong> caractères)<br />
Y a-t-il <strong>de</strong>s caractères indésirables dans la chaîne saisie ?<br />
Que se passe-t-il si l'utilisateur entre plus <strong>de</strong> 20 caractères ? Comment remédier à ce problème ?<br />
Écrire une fonction qui "n<strong>et</strong>toie" une chaîne saisie par fg<strong>et</strong>s (en enlevant le caractère '\n' résiduel).<br />
II. Traitements sur les chaînes<br />
II.1. Écrire une fonction qui compte le nombre <strong>de</strong> caractères contenus dans une chaîne. Comparer les résultats<br />
obtenus avec la fonction strlen.<br />
II.1.a. 2 Comparer les temps d'exécution <strong>de</strong> votre fonction par rapport à strlen. On pourra utiliser pour cela la<br />
fonction difftime (définie dans time.h) appliquée sur un très grand nombre d'appels <strong>de</strong> chacune <strong>de</strong>s fonctions.<br />
Essayer d'optimiser votre fonction afin qu'elle s'exécute en un temps minimal.<br />
II.2. Écrire une fonction qui compte le nombre <strong>de</strong> voyelles contenues dans une chaîne <strong>de</strong> caractères (sans<br />
distinction <strong>de</strong>s minuscules <strong>et</strong> majuscules).<br />
II.3. Écrire une fonction qui compte le nombre <strong>de</strong> mots contenus dans une chaîne.<br />
III. Interprétation d'une chaîne <strong>de</strong> caractères.<br />
III.1. Faire la saisie d'une chaîne donnée sous la forme : valeur numérique opérateur valeur numérique<br />
Par exemple : "2.4 + -3.5"<br />
L'opérateur pourra être un caractère parmi +, -, *, / <strong>et</strong> ^ (élévation à la puissance)<br />
Faire une fonction qui r<strong>et</strong>ourne la valeur numérique correspondant à l'expression écrite dans la chaîne. On pourra<br />
utiliser la fonction strtod pour l'évaluation <strong>de</strong>s données numériques.<br />
III.2. 2 Améliorer c<strong>et</strong>te fonction pour qu'elle prenne en charge les parenthèses, perm<strong>et</strong>tant ainsi d'écrire par<br />
exemple : 2.4 + (-3.5)<br />
Pourrait-on envisager d'évaluer une expression du type : 2.4 + (0.5-4.0)<br />
2 Exercices optionnels
TP3 : TABLEAUX DE DONNÉES<br />
I. Acquisition <strong>de</strong> données<br />
I.1. Déclarer un tableau <strong>de</strong> 40 entiers<br />
Écrire une fonction perm<strong>et</strong>tant <strong>de</strong> saisir au clavier les nb premiers éléments du tableau (0 ≤ nb < 40).<br />
Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
void AcqTab(int *tab, unsigned nb);<br />
I.2. Écrire une fonction affichant à l'écran les n premiers nombres d'un tableau, en passant une ligne toutes les nbl<br />
valeurs.<br />
Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
void AffTab(int *tab, unsigned n, unsigned nbl);<br />
II. Nombres aléatoires<br />
II.1. Écrire une fonction qui remplit un tableau avec n valeurs aléatoires. On utilisera la fonction rand(), définie<br />
dans stdlib.h. Afficher les résultats obtenus.<br />
Exécuter plusieurs fois le programme. Conclure.<br />
II.2. 3 Initialiser le générateur <strong>de</strong> nombres aléatoires en utilisant la fonction srand() (voir prototype). L'initialisation<br />
sera réalisée à l'ai<strong>de</strong> <strong>de</strong> la fonction time() (définie dans time.h).<br />
Observer <strong>de</strong> nouveau les résultats obtenus.<br />
II.3. Écrire une nouvelle fonction qui effectue un tirage <strong>de</strong> 6 valeurs aléatoires distinctes, <strong>et</strong> comprises entre 1 <strong>et</strong> 49.<br />
Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
unsigned *Loto(void);<br />
C<strong>et</strong>te fonction r<strong>et</strong>ourne un pointeur sur le tableau contenant les 6 valeurs du tirage.<br />
III. Tris<br />
III.1. Constituer un tableau <strong>de</strong> N valeurs aléatoires. Classer en ordre croissant ce tableau en utilisant les algorithmes<br />
suivants :<br />
tri à bulle<br />
tri par sélection<br />
tri <strong>de</strong> Hoare<br />
III.2. 3 Mesurer les durées d'exécution <strong>de</strong>s différents algorithmes appliqués sur les mêmes tableaux, en utilisant la<br />
fonction clock() pour différentes valeurs <strong>de</strong> N.<br />
Comparer les résultats obtenus avec la fonction qsort() définie dans stdlib.h.<br />
III.3. Définir un tableau <strong>de</strong> chaînes <strong>de</strong> caractères.<br />
Classer en ordre croissant, puis en ordre décroissant ce tableau en utilisant la fonction qsort.<br />
3 Exercices optionnels.
TP4 : FICHIERS<br />
I. Lecture d'un fichier texte<br />
Éditer (avec un éditeur <strong>de</strong> textes) un texte quelconque <strong>de</strong> quelques lignes.<br />
Enregistrer ce fichier sur le disque.<br />
Créer un programme qui lit ce fichier <strong>et</strong> affiche son contenu. Le programme affichera finalement le nombre <strong>de</strong><br />
lignes composant le fichier.<br />
II. Cryptage d'un fichier<br />
On se propose <strong>de</strong> crypter <strong>de</strong> manière simple le fichier précé<strong>de</strong>mment créer (afin d'en interdire la lecture avec un<br />
simple éditeur <strong>de</strong> textes).<br />
II.1. Faire la fonction <strong>de</strong> cryptage<br />
L'oct<strong>et</strong> transmis sera divisé en <strong>de</strong>ux quart<strong>et</strong>s. Les bits <strong>de</strong>s quart<strong>et</strong>s seront ensuite mélangés comme indiqué ci<strong>de</strong>ssous.<br />
La fonction r<strong>et</strong>ournera le complément du résultat obtenu.<br />
Exemple : Soit le caractère 'A' <strong>de</strong> co<strong>de</strong> ASCII 0x41<br />
On coupe ce co<strong>de</strong> ASCII en <strong>de</strong>ux quart<strong>et</strong>s ; on obtient 4 <strong>et</strong> 1, soit en binaire : 0100 <strong>et</strong> 0001.<br />
On mélange les quart<strong>et</strong>s en alternant les bits :<br />
0 1 0 0<br />
0 0 0 1<br />
0<br />
1 0 0 1 0 0 0<br />
On obtient alors un oct<strong>et</strong> contenant 0x48, soit, en binaire : 01001000<br />
Ensuite on prend le complément <strong>de</strong> c<strong>et</strong>te valeur <strong>et</strong> on obtient 10110111, soit en hexadécimal 0xB7.<br />
Si le caractère 'A' est transmis à la fonction, celle-ci r<strong>et</strong>ournera donc la valeur B7 H (soit 183 en décimal).<br />
II.2. Écrire une fonction réalisant la lecture du fichier Fin, qui crypte ce fichier <strong>et</strong> écrit le résultat dans Fout.<br />
Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
int CryptFile(FILE *Fin, FILE *Fout);<br />
C<strong>et</strong>te fonction r<strong>et</strong>ournera 1 si le cryptage s'est bien passé, <strong>et</strong> 0 en cas d'erreur.<br />
Remarque : Le fichier Fout <strong>de</strong>vra avoir été ouvert en binaire pour assurer une écriture correcte dans le fichier.<br />
II.3. Faire le programme compl<strong>et</strong>.<br />
L'utilisateur <strong>de</strong>vra entrer le nom du fichier à crypter <strong>et</strong> le nom du fichier crypté.<br />
II.4. 4 On souhaite appeler le programme <strong>de</strong> cryptage selon la syntaxe suivante :<br />
NomProg NomFichier<br />
où NomProg est le nom du programme exécutable (.exe) <strong>et</strong> NomFichier est le nom du fichier à crypter.<br />
Le fichier transmis sera alors crypté, le résultat étant mis à la place du fichier d'origine.<br />
Faire la lecture <strong>de</strong>s arguments <strong>de</strong> la fonction main(), en sachant que le prototype <strong>de</strong> main() est<br />
int main(int argc, char *argv[]);<br />
où argc représente le nombre d'arguments sur la ligne <strong>de</strong> comman<strong>de</strong> (y compris le nom du programme) <strong>et</strong> argv est<br />
un tableau <strong>de</strong> chaînes <strong>de</strong> caractères contenant les différents arguments.<br />
Écrire le programme compl<strong>et</strong>. On pourra utiliser les fonctions tmpnam() , rename() <strong>et</strong> remove() en s'assurant que le<br />
fichier d'origine ne doit être détruit que si le fichier crypté a été construit sans erreur.<br />
Proposer un système perm<strong>et</strong>tant <strong>de</strong> crypter ou décrypter <strong>de</strong> manière automatique le fichier transmis en argument.<br />
4 Exercice optionnel.
TP5 : STRUCTURES<br />
I. Définition d'une structure<br />
Définir un type <strong>de</strong> structure TInfo pouvant contenir <strong>de</strong>s informations sur <strong>de</strong>s personnes :<br />
le nom (chaîne <strong>de</strong> caractères - maximum 40 caractères)<br />
le prénom (chaîne <strong>de</strong> caractères - maximum 40 caractères)<br />
le jour <strong>de</strong> naissance (entier court - char)<br />
le mois <strong>de</strong> naissance (entier court - char)<br />
l'année <strong>de</strong> naissance (entier court - short)<br />
le numéro <strong>de</strong> téléphone (tableau <strong>de</strong> 15 entiers courts – type char)<br />
le nombre <strong>de</strong> chiffres composant le numéro <strong>de</strong> téléphone (entier court - char)<br />
l'adresse Email (chaîne <strong>de</strong> caractères - maximum 60 caractères)<br />
II. Encombrement mémoire<br />
Observer (avec l'opérateur sizeof) l'encombrement mémoire <strong>de</strong> c<strong>et</strong>te structure.<br />
III. Tableau <strong>de</strong> structures<br />
Définir un tableau perm<strong>et</strong>tant <strong>de</strong> mémoriser 1000 structures TInfo, en initialisant les <strong>de</strong>ux premières structures avec<br />
vos coordonnées.<br />
Indiquer l'encombrement mémoire <strong>de</strong> ce tableau.<br />
IV. Acquisition <strong>de</strong>s champs<br />
Ecrire une fonction perm<strong>et</strong>tant d'acquérir au clavier une structure TInfo.<br />
C<strong>et</strong>te fonction posera les questions suivantes :<br />
Entrer le nom :<br />
Entrer le prénom :<br />
Entrer la date <strong>de</strong> naissance sous la forme jj/mm/aaaa :<br />
Entrer le numéro <strong>de</strong> téléphone (max 15 chiffres) :<br />
Entrer l'Email :<br />
Le prototype <strong>de</strong> c<strong>et</strong>te fonction sera :<br />
void AcqInfo(struct TInfo *info);<br />
V. Acquisition <strong>et</strong> enregistrement dans un fichier<br />
Faire un programme perm<strong>et</strong>tant d'acquérir au clavier <strong>de</strong>s informations sur <strong>de</strong>s personnes <strong>et</strong> <strong>de</strong> les enregistrer dans<br />
un fichier disque. On pourra utiliser pour ceci la fonction fwrite(), définie dans stdio.h.<br />
Le fichier créé peut-il être visualisé à l'ai<strong>de</strong> d'un simple éditeur <strong>de</strong> textes ?<br />
VI. Relecture du fichier<br />
Modifier le programme précé<strong>de</strong>nt pour initialiser le tableau <strong>de</strong> structures à partir du fichier enregistré sur le disque,<br />
s'il existe.<br />
VII. 5 Classement <strong>de</strong>s informations.<br />
Réaliser le tri du tableau <strong>de</strong> structures selon différents critères (par exemple, le nom, le prénom ou l'âge).<br />
5 Exercice optionnel
TP6 : ÉTUDE DE FONCTIONS MATHÉMATIQUES<br />
I. Définition <strong>de</strong> fonctions mathématiques<br />
Écrire les fonctions (informatiques) perm<strong>et</strong>tant <strong>de</strong> calculer les fonctions mathématiques suivantes :<br />
f ( x)<br />
=<br />
1<br />
10<br />
∑<br />
sin<br />
((2<br />
⋅i<br />
+ 1) ⋅ x)<br />
i= 0 2 ⋅i<br />
+<br />
1<br />
sin( x)<br />
f<br />
2<br />
( x)<br />
= f<br />
3(<br />
x)<br />
= sin(10 ⋅ x)<br />
⋅ exp( −x)<br />
x<br />
Constituer un tableau <strong>de</strong> pointeurs <strong>de</strong> fonctions, perm<strong>et</strong>tant d'accé<strong>de</strong>r par la suite aux fonctions préalablement<br />
définies.<br />
II. Calcul <strong>de</strong>s fonctions<br />
Écrire un programme qui <strong>de</strong>man<strong>de</strong> à l'utilisateur :<br />
le numéro <strong>de</strong> la fonction qu'il souhaite étudier (1, 2 ou 3)<br />
la valeur minimale <strong>de</strong> l'abscisse (Xmin)<br />
la valeur maximale <strong>de</strong> l'abscisse (Xmax)<br />
le nombre <strong>de</strong> points à utiliser pour l'étu<strong>de</strong> (nbp)<br />
Le programme <strong>de</strong>vra créer <strong>de</strong> manière dynamique un tableau perm<strong>et</strong>tant <strong>de</strong> ranger les nbp points calculés (les<br />
ordonnées) <strong>de</strong> la fonction (utiliser malloc(), définie dans stdlib.h)<br />
On cherchera ensuite dans ce tableau les valeurs minimale <strong>et</strong> maximale <strong>de</strong> la fonction. Ces informations seront<br />
affichées à l'écran.<br />
Remarque : On n'oubliera pas <strong>de</strong> libérer l'espace mémoire alloué dynamiquement dès que les données ne sont plus<br />
nécessaires (utilisation <strong>de</strong> free()).<br />
III. Traitement <strong>de</strong>s exceptions.<br />
Dans certains cas, la fonction mathématique peut déclencher une erreur (par exemple une division par 0). Prévoir la<br />
résolution du problème en utilisant la fonction signal(), définie dans signal.h. C<strong>et</strong>te fonction perm<strong>et</strong> l'appel d'une<br />
fonction <strong>de</strong> gestion d'erreur dès qu'un "signal" est capté. Dans notre cas, on utilisera le signal SIGFPE (Floating<br />
Point Exception).<br />
IV. Ecriture <strong>de</strong>s résultats dans un fichier<br />
Écrire une fonction perm<strong>et</strong>tant <strong>de</strong> ranger les couples (abscisses, ordonnées) dans un fichier texte. Chaque ligne du<br />
fichier qui contiendra les valeurs <strong>de</strong> l'abscisse <strong>et</strong> <strong>de</strong> l'ordonnée, séparées par un caractère ';'.<br />
Ce fichier pourra être récupéré par un autre programme, comme un tableur (type Excel) <strong>et</strong> ceci perm<strong>et</strong>tra ainsi <strong>de</strong><br />
manière simple <strong>de</strong> réaliser le tracé <strong>de</strong> la fonction 6 .<br />
V. Écriture d'une fonction <strong>de</strong> gestion d'erreur<br />
Le programme écrit peut provoquer <strong>de</strong>s erreurs. Écrire une fonction perm<strong>et</strong>tant <strong>de</strong> m<strong>et</strong>tre fin au programme<br />
(utiliser la fonction exit()), en affichant un message d'erreur explicite.<br />
C<strong>et</strong>te fonction aura le prototype suivant (<strong>et</strong> utilisera vprintf()) :<br />
void ErrPrintf(const char *format, ...);<br />
On pourra ainsi appeler c<strong>et</strong>te fonction <strong>de</strong> la manière suivante :<br />
ErrPrintf("Xmax [%G] doit être supérieur à Xmin [%G].",Xmax,Xmin);<br />
ou bien :<br />
ErrPrintf("Le fichier '%s' ne peut être ouvert",nom_fichier);<br />
<strong>et</strong>c.…<br />
6 Exercice facultatif.
TP7 : ACQUISITION ET TRAITEMENT DE DONNÉES<br />
I. Signal analogique<br />
I.1 Échantillonner un signal analogique avec les cartes d'entrées-sorties.<br />
On prendra :<br />
F E = 1KHz<br />
Nombre d'échantillons = 1024<br />
I.2. Déterminer numériquement :<br />
• Les valeurs extrêmes du signal (en volts)<br />
• La valeur <strong>et</strong> l'instant <strong>de</strong> la plus forte pente<br />
II. Filtre numérique.<br />
On m<strong>et</strong> en œuvre un filtre dont l'équation <strong>de</strong> récurrence s'écrit :<br />
ek+<br />
1<br />
− yk<br />
yk+<br />
1<br />
= yk<br />
+<br />
U<br />
N<br />
Déterminer expérimentalement la nature du filtre.<br />
La fréquence d'échantillonnage est égale à 1 kHz.<br />
Quels sont le gain <strong>et</strong> la fréquence <strong>de</strong> coupure pour N = 1 <strong>et</strong> N = 16<br />
filtre<br />
Y