11.07.2015 Views

Transparents du cours - INSA de Lyon

Transparents du cours - INSA de Lyon

Transparents du cours - INSA de Lyon

SHOW MORE
SHOW LESS
  • No tags were found...

Create successful ePaper yourself

Turn your PDF publications into a flip-book with our unique Google optimized e-Paper software.

AGP: Algorithmique et programmationTanguy Risset, Stéphane Ubébatanguy.risset@insa-lyon.fr, Stéphane.Ubéda@insa-lyon.frLab CITI, <strong>INSA</strong> <strong>de</strong> <strong>Lyon</strong>Version <strong>du</strong> November 20, 2007- p. 1/81Présentation <strong>du</strong> <strong>cours</strong>intro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctions■■ Enseignants:◆ Cours 24h: Tanguy Risset, Stéphane Ubeda◆ TD 30:◆ TP 28h■ Déroulement <strong>du</strong> <strong>cours</strong>:◆ Principes <strong>de</strong> la programmation en C◆ Principes <strong>de</strong> l’algorithmique◆ Notions <strong>de</strong> recherche opérationnelleErreurs courante en C- p. 2/81


Références utilesintro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ livres:◆ Le langage C, Kernighan & Ritchie, Masson, 1990la référence pour la programmation en C ANSI◆ Intro<strong>du</strong>ction à l’algorithmique, T. Cormen, C. Leiserson, R.Rivest, 1994, DunodApproche complète et pédagogique <strong>de</strong> l’algorithmique■ Sur le web◆ Poly <strong>de</strong> Bernard Cassagne (votre poly):http://www-clips.imag.fr/commun/bernard.cassagne/Intro<strong>du</strong>ction_ANSI_C.htm◆ C reference manual (version épurée <strong>du</strong> Kernighan &Ritchie avec grammaire <strong>du</strong> langage):http://cm.bell-labs.com/cm/cs/who/dmr/cman.pdf◆ C library reference gui<strong>de</strong>:http://www.acm.uiuc.e<strong>du</strong>/webmonkeys/book/c_gui<strong>de</strong>/◆ Cours d’Anne Canteaut (beaucoup utilisé dans cestransparents)http://www-rocq.inria.fr/co<strong>de</strong>s/Anne.Canteaut/COURS_C/- p. 3/81Intro<strong>du</strong>ctionintro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Historique◆ Créé par Dennis Ritchie pour écrire Unix pour le PDP-11(publication 1978)◆ Standard ANSI C (1990)■ Pourquoi C?◆ Avantages■ Performance(http://shootout.alioth.<strong>de</strong>bian.org),portabilité, standard, proche <strong>de</strong> la machine■ Permet <strong>de</strong> comprendre les mécanismes <strong>de</strong> l’exécution<strong>de</strong> programmes ⇒ bonnes bases pour tous les autreslangages (bibliothèques, portabilité, etc.).◆ Inconvénients■ Dangereux (bugs!), nécessite beaucoup <strong>de</strong> rigueur,programmation bas niveau,■ Peu adapté aux ordinateurs non standard (temps réel,systèmes distribués, parallélisme, etc.)- p. 4/81


Rappels sur l’architecture d’un ordinateurintro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Un ordinateur <strong>de</strong> bureau est composé (au moins):◆ D’un processeur◆ D’une mémoire (dite vive: rapi<strong>de</strong> et non rémanente)◆ D’un espace <strong>de</strong> stockage (disque <strong>du</strong>r: lent, rémanent)◆ De périphériques d’entrée/sortie (écran, claviers, etc.)■ Principe <strong>du</strong> processeur programmable:◆ Le processeur lit un programme en mémoire (programmeexécutable, dépendant <strong>du</strong> type <strong>de</strong> processeur).◆ En fonction <strong>de</strong> ce programme■ Il lit ou écrit <strong>de</strong>s données en mémoire à une certaineadresse mémoire (nombre entier sur 32 bits)■ Il effectue <strong>de</strong>s calculs entre ces données- p. 5/81Rappels d’architectureintro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> CProcessorInterrupts7fffffff hexStack segLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionCacheMemory–I/O busDynamic dataStatic dataData segmPointeur <strong>de</strong> fonctionsErreurs courante en CMainmemoryI/OcontrollerI/OcontrollerI/Ocontroller10000000 hexText segmDiskDiskGraphicsoutputNetwork400000 hexReserved- p. 6/81


Architecture vue <strong>du</strong> programmeurintro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Les systèmes mo<strong>de</strong>rnes permettent◆ D’exécuter plusieurs programmes indépendant enparallèle (processus)◆ D’accé<strong>de</strong>r à un espace mémoire plus grand que lamémoire physique disponible (mémoire virtuelle)■ Pour le programmeur: tout cela est transparent◆ Un seul programme s’exécute avec une mémoire trèsgran<strong>de</strong> disponible■ La mémoire vue <strong>du</strong> processeur contient:◆ Le co<strong>de</strong> à exécuter◆ Les données statiques (taille connue à la compilation)◆ Les données dynamiques (taille connues à l”exécution: letas, et l’espace necessaire à l’exécution elle-meme: lapile)■ Le programmeur lui ne voit que les données (statiques etdynamiques)- p. 7/81Processus <strong>de</strong> compilationintro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> C■ le processus complet va tra<strong>du</strong>ire un programme C en co<strong>de</strong>exécutable (le chargement et l’exécution auront lieu plustard).co<strong>de</strong>asm.ccompilateur.sassembleurobj.oLes fonctionsLes entrées-sortieslib.aédition <strong>de</strong>sliensIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsExécutionSimulationchargementexeErreurs courante en C■ On nomme souvent compilation l’ensemblecompilateur+assembleur■ Le compilateur GCC inclut aussi un assembleur et un éditeur<strong>de</strong> lien (accessibles par <strong>de</strong>s options)- p. 8/81


Votre processus <strong>de</strong> compilationintro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties■ Le programmeur:◆ Écrit le programme C: ici le dans le fichier ex.c◆ Compile vers un programme objet ex.o◆ Fait l’édition <strong>de</strong> lien pour générer l’executable excontenu <strong>de</strong> ex.cex.cgcc −c ex.cex.oIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsstdio.hlibstdio.agcc ex.o −o exErreurs courante en Cgcc ex.c −o exex- p. 9/81Dénomination à retenirintro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Le programme C que vous écrivez est le programme source(ex.c)■ Le programme source est compilé en un programme objetpar le compilateur (ex.o)■ Le programme source inclut un fichier d’en-tete (stdio.h)pour vérifier les noms <strong>de</strong>s fonctions externes utilisées(printf)■ le programme executable est construit par l’éditeur <strong>de</strong> liensgrâce au programme objet et aux bibliothèques.■ Les bibliothèques (library enex.cgcc −c ex.canglais) sont <strong>de</strong>s co<strong>de</strong>sassembleurs (i.e. déjà compilés) <strong>de</strong>stdio.hfonctions fréquements utilisées. Icila bibliothèque utilisée estlibstdio.a qui contient le co<strong>de</strong><strong>de</strong> la fonction printflibstdio.agcc ex.c −o exex.ogcc ex.o −o eex- p. 10/81


Notions <strong>de</strong> génie logicielintro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Pour développer une application, on parle <strong>de</strong> logiciel plutôtque <strong>de</strong> programme■ Un logiciel est plus qu’un programme■ Le cycle <strong>de</strong> vie <strong>du</strong> logiciel inclut:◆ L’analyse <strong>du</strong> problème à résoudre◆ La conception d’une solution (spécification)◆ Le développement <strong>de</strong> la solution (programme)◆ Le test <strong>du</strong> programme◆ La livraison avec documentation associée◆ La maintenance- p. 11/81Outils pour le développement logicielintro<strong>du</strong>ction● Présentation <strong>du</strong> <strong>cours</strong>● Intro<strong>du</strong>ction● Rappels d’architecture● Rappels d’architecture● Compilation● logicielLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Métho<strong>de</strong>s◆ Réfléchir avant d’agir !◆ règles <strong>de</strong> développement (Merise, programmation partest)◆ Language objet: C++, Java■ Outils◆ Gestionnaire <strong>de</strong> compilation : make◆ Debugger : gbd, ddd, ....◆ Environnements <strong>de</strong> développement (intègrent tout):eclipse, VisualC++- p. 12/81


Les bases <strong>du</strong> Cintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Instruction, expression, programme■ Éléments <strong>de</strong> base◆ Variable et types <strong>de</strong> base◆ Opérateurs◆ Types construits◆ Opération <strong>de</strong> Contrôle <strong>de</strong> flôt◆ Fonctions et passage <strong>de</strong> paramètres◆ Entrées-sorties◆ Visibilité et <strong>du</strong>rée <strong>de</strong> vie <strong>de</strong>s variables■ Exemple: le tri d’un tableau d’entier- p. 13/81Syntaxeintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ La syntaxe est définie par <strong>de</strong>s règles <strong>de</strong> grammaire.■ Extrait <strong>de</strong> la grammaire:expression::primary| expression binop expression| expression asgnop expression| ....primary::i<strong>de</strong>ntifier| string| constant| ...■ x = 0 , a + b, a+=1 sont syntaxiquement corrects(respectent la grammaire)asgnop::=| +=| ...binop::+| -| ...■ Un programme syntaxiquement correct n’est pas forcémentun programme C vali<strong>de</strong>. Exemple: 1 = 0 estsyntaxiquement correct mais sémantiquement incorrect.- p. 14/81


Expression, Instructionintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Une expression est une suite <strong>de</strong> composants élémentaires syntaxiquement correcte,par exemple: x = 0 ou bien(i >= 0) && (i < 10)■ En C chaque expression pro<strong>du</strong>it:◆ une action (modification possible <strong>de</strong> l’état <strong>de</strong>s variables en mémoire)◆ un résultat (valeur renvoyée par l’expression)■ Une instruction est une expression suivie d’un point-virgule. Le point-virgule signifie enquelque sorte “évaluer cette expression et oublier le resultat”.■ Plusieurs instructions peuvent être rassemblées par <strong>de</strong>s accola<strong>de</strong>s { et } pour formerune instruction composée (ou bloc) qui est syntaxiquement équivalent à uneinstruction. Par exemple,if (x != 0){z = y / x;t = y % x;}- p. 15/81Structure d’un programme Cintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Un programme C se présente <strong>de</strong> la façon suivante :directives au préprocesseurdéclarations <strong>de</strong> variables globalesfonctions secondairesint main(){ déclarations <strong>de</strong> variables internesinstructions}■ La fonction main est exécutée lors <strong>de</strong> l’exécution <strong>du</strong>programme.■ Le résultat <strong>de</strong> la fonction main est le résultat <strong>de</strong> l’exécution<strong>du</strong> programme (co<strong>de</strong> d’erreur en général)- p. 16/81


Variablesintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ La notion <strong>de</strong> variable est très importante en programmation■ Du point <strong>de</strong> vue sémantique, une variable est une entité quicontient une information :◆ Une variable possè<strong>de</strong> un nom, on parle d’i<strong>de</strong>ntifiant◆ Une variable possè<strong>de</strong> une valeur qui change au <strong>cours</strong> <strong>de</strong>l’exécution <strong>du</strong> programme◆ Une variable possè<strong>de</strong> un type qui caractérise l’ensemble<strong>de</strong>s valeurs qu’elle peut prendre■ Du point <strong>de</strong> vue pratique, une variable est une manièremnémotechnique pour désigner une partie <strong>de</strong> la mémoire.■ En C les noms <strong>de</strong>s variables sont composés <strong>de</strong> la manièresuivante:une suite <strong>de</strong> caractères parmis :◆ les lettres (minuscules ou majuscules, mais nonaccentuées),◆ les chiffres (sauf en début <strong>de</strong> nom),◆ le “blanc souligné” (_).- p. 17/81Types <strong>de</strong> base en Cintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ En C, les variables doivent être déclarées avant d’êtreutilisées, on dit que C est un langage typé■ Les types <strong>de</strong> base en C sont désignés par <strong>de</strong>s spécificateurs<strong>de</strong> type qui sont <strong>de</strong>s mots clefs <strong>du</strong> langages:◆ les caractères (char),◆ les entiers (int, short, , unsigned long)◆ les flottants (nombres réels, float, double).◆ Il n’y a pas <strong>de</strong> type booleen, ils sont codés par <strong>de</strong>s int■ Une instruction composée d’un spécificateur <strong>de</strong> type etd’une liste d’i<strong>de</strong>ntificateurs éventuellement initialisés séparéspar une virgule est une déclaration. Par exemple:int a;int b = 1, c;double x = 2.38e4;char message[80];■ Il existe <strong>de</strong> nombreuses conversions <strong>de</strong> types implicites- p. 18/81


Représentation <strong>de</strong> l’informationintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Le type d’une variable indique au compilateur la manière <strong>de</strong>stocker la variabe en mémoire■ Il est important <strong>de</strong> connaître comment sont stockées lesvariables car C propose <strong>de</strong> nombreuses manipulations auniveau bit.■ La mémoire est une suite <strong>de</strong> bit structurée en octets (8 bits)puis en mots (4 octets, 32 bits).■ L’adresse 1084 doit se lire comme “le 1084 eme octet <strong>de</strong> lamémoire”■ On utilisera trois notations pour représenter les valeursentières en mémoire.◆ La notation décimale usuelle (10 chiffres): 12 <strong>de</strong>c vaut lavaleur 12◆ La notation binaire (2 chiffres): 1100 bin vaut la valeur 12◆ La notation hexadécimale (16 chiffres) C hex vaut la valeur12 (essentiellement pour représenter les adresses).- p. 19/81Les types entiersintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en Cmot-clef taille dénomination remarqueschar 8 bits caractère peut être utilisé comme entiershort 16 bits entier courtint 32 bits entierlong >=32 bits entier long souvent 64 bits■ En C les entiers signés sont représentés en complément à2, c’est à dire (pour un entier n sur 32 bit):◆ le bit <strong>de</strong> poids fort (bit 32) représente le signe (0 pourpositif, 1 pour négatif)◆ Si l’entier est positif: les 31 autres bits correspon<strong>de</strong>nt à ladécomposition <strong>de</strong> l’entier en base 2.◆ Si l’entier est négatif les 31 autres bits correspon<strong>de</strong>nt à ladécomposition <strong>de</strong> l’entier 2 31 − |n|◆ pour int n; on a donc les contraintes: −2 31


Les types entierintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Les mots-clef <strong>de</strong>s types peuvent être précédés d’attributs.Par exemple unsigned int n indique que l’entier n estpositif, la représentation en complément à <strong>de</strong>ux n’est pasutilisée on a alors 0


Les caractèresintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Un char peut contenir n’importe quel élément <strong>du</strong> jeu <strong>de</strong> caractères <strong>de</strong> la machineutilisée.■ un char est codé sur un octet ;■ Le jeu <strong>de</strong> caractères utilisé correspond généralement au codage ASCII (sur 7 bits).■ La plupart <strong>de</strong>s machines utilisent désormais le jeu <strong>de</strong> caractères ISO-8859-1 (aussiappelée ISO-LATIN-1) dont les 128 premiers caractères correspon<strong>de</strong>nt aux caractèresASCII.■ extrait <strong>de</strong> la table ASCII:caractère valeur valeur · caractère valeur valeurreprésenté (<strong>de</strong>c) (hex) représenté (<strong>de</strong>c) (hex)! 33 21 hex A 65 41 hex" 34 22 hex B 66 42 hex# 35 23 hex C 67 43 hex. . . . . . . . . . . . . . . . . .0 48 30 hex a 97 61 hex1 49 31 hex b 98 62 hex2 50 32 hex . . . . . . . . .- p. 23/81Les constantesintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Les valeurs exprimées dans un programme C sont <strong>de</strong>sconstantes■ Les constantes entière peuvent être exprimées en décimal(int i=12) ou en hexadécimal (int i=0xA),■ On peut aussi indiquer qu’elle doivent être stockées sur unlong (12L) ou en unsigned (12U).■ Les constantes réelles suivent le même principe■ 12.34 (double), 12.3e-4, (double), 12.34F (float),12.34L (Long)■ Les caractères imprimable sont repérentés entre cotes (’):char a=’Z’■ Les caractères non imprimables sont représentés en co<strong>de</strong>octal (base 8) précédé d’un antislash, Les plus fréquent ont<strong>de</strong>s représentations standard: \n nouvelle ligne, \r retourchariot, \t tabulation horizontale\f saut <strong>de</strong> page,- p. 24/81


Constantes et variablesintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctions■ La notion <strong>de</strong> constante n’est pas limitée aux valeurs fixes■ Une constante est une valeur non modifiable, par exemplel’adresse d’une variable.■ Il existe une différence fondamentale avec les variables: iln’y a pas <strong>de</strong> place réservée pour une constante dans lamémoire lors <strong>de</strong> l’exécution d’un programme.■ C’est le compilateur qui met en <strong>du</strong>r la valeur <strong>de</strong> la constantelorsqu’il génère l’instruction:j=i+10⇒ add Rj,Ri,#10Erreurs courante en C- p. 25/81Les opérateursintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ affectation: variable = expression■ opérateurs arithmétiques +,-,*,/,%,expression-1 op expression-2■ opérateurs relationnels >,=,


Règles <strong>de</strong> priorité <strong>de</strong>s opérateursintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ les opérateurs sont plus ou moins prioritaires,■ Dans le cas <strong>de</strong> priorité égales on a un ordre d’évaluation(associatifs à droite ou à gauche)■ ordre <strong>de</strong> priorité:opérateurs() [] -> . droiteassociativité! ++ – -(unaire) (type) *(indirection) &(adresse) sizeof gauche* / % droite+ -(binaire) droite« » droite< >= droite== != droite&(et bit-à-bit)droite| droite&&droite|| droite? : gauche= += -= *= /= %= &= ˆ= |= «= »= gauche, droite- p. 27/81Types construitsintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ À partir <strong>de</strong>s types prédéfinis <strong>du</strong> C (caractères, entiers,flottants), on peut créer <strong>de</strong> nouveaux types, appelés typescontruits, qui permettent <strong>de</strong> représenter <strong>de</strong>s ensembles <strong>de</strong>données organisées.■ Les tableaux■ Les structures■ Les unions■ Les énumérations■ Les constructeurs <strong>de</strong> type- p. 28/81


Les tableauxintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Un tableau est un ensemble fini d’éléments <strong>de</strong> même type,stockés en mémoire à <strong>de</strong>s adresses contiguës.■ La déclaration d’un tableau tab <strong>de</strong> 10 entiers se fait <strong>de</strong> lafaçon suivante : int tab[10];■ On accè<strong>de</strong> au troisième élément <strong>du</strong> tableau tab parl’expression tab[2]. Les tableaux en C commencenttoujours à 0.■ On peut définir <strong>de</strong>s tableaux multidimensionnels. Exemple:matrice M d’entiers <strong>de</strong> 10 lignes 5 colonnes int M[10][5]■ Important: un tableau en C peut être vu comme un pointeursur le premier élément <strong>du</strong> tableau:int *tab; ⇔ int tab[];■ Mais il faut savoir qu’en C un tableau est une constante- p. 29/81Tableaux: exempleintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortieschar tab[10] = {’e’,’x’,’e’,’m’,’p’,’l’,’e’,’\0’};main(){int i;for (i = 0; i < 10; i++)printf("tab[%d] = %c\n",i,tab[i]);}Intro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en Ctab[0] = etab[1] = xtab[2] = etab[3] = mtab[4] = ptab[5] = ltab[6] = etab[7] =tab[8] =tab[9] =- p. 30/81


Tableaux: exempleintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C#<strong>de</strong>fine M 2#<strong>de</strong>fine N 3int tab[M][N] = {{1, 2, 3}, {4, 5, 6}};main(){int i, j;for (i = 0 ; i < M; i++){for (j = 0; j < N; j++)printf("tab[%d][%d]=%d\n",i,j,tab[i][j]);}}tab[0][0]=1tab[0][1]=2tab[0][2]=3tab[1][0]=4tab[1][1]=5tab[1][2]=6- p. 31/81Retour sur les types: les chaînes <strong>de</strong> caractèresintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ En C une chaine <strong>de</strong> caractères n’est pas un type <strong>de</strong> base:c’est un tableau <strong>de</strong> caractères terminé par le caractèrespécial ’\0’ (ou NULL: octet valant 0).■ On peut la noter entre double cote:char chaine[10]="bonjour"■ Où comme un tableau <strong>de</strong> caractère (jamais utilisé):char chaine[10]={’b’,’o’,’n’,’j’,’o’,’u’,’r’,’\0’}■ Comme un tableau en C est assimilé à un pointeur sur ledébut <strong>du</strong> tableau on trouvera souvent <strong>de</strong>s chaines <strong>de</strong>caractères déclarées comme:char *chaine;■ Pour l’instant on preferera la déclaration statique (tableau).Attention il faut une case <strong>de</strong> plus que le nombre <strong>de</strong> lettres(pour ’\0’).- p. 32/81


Les structuresintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Une structure est une suite finie d’objets <strong>de</strong> types différents.■ Contrairement aux tableaux, les différents éléments d’unestructure n’occupent pas nécessairement <strong>de</strong>s zonescontiguës en mémoire.■ Chaque élément <strong>de</strong> la structure, appelé membre ou champ,est désigné par un i<strong>de</strong>ntificateur.■ Deux manières équivalentes <strong>de</strong> définir une variable zcomplexe:struct complexestruct complexe{{double reelle;double reelle;double imaginaire; double imaginaire;} z;};struct complexe z;norme=sqrt(z.reelle*z.reelle+z.imaginaire*z.imaginaire);- p. 33/81Les structures <strong>de</strong> contrôle <strong>de</strong> flotintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flot■ Les objets que nous avons rencontrés permettent <strong>de</strong> faire<strong>de</strong>s calculs, pas <strong>de</strong> contrôler quels calculs sont faits■ Les structures <strong>de</strong> contrôles sont <strong>de</strong> <strong>de</strong>ux types:◆ Les boucles◆ Les instructions <strong>de</strong> branchementLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C- p. 34/81


Les bouclesintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Boucles while:while (expression )instruction■ Boucles forfor (expr 1 ;expr 2 ;expr 3)instructioni = 1;while (i < 10){printf(" i = %d \n",i);i++;}⇔expr 1;while (expr 2 ){instructionexpr 3;}- p. 35/81Les instructions <strong>de</strong> branchementintro<strong>du</strong>ctionLes bases <strong>du</strong> C● Syntaxe● types <strong>de</strong> base● Les opérateurs● Types construits● Les tableaux● chaînes <strong>de</strong> caractères● contrôle <strong>de</strong> flotLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Branchement conditionnelif (expression-1 )instruction-1else instruction-2ouif (expression-1 )instruction-1■ Branchement multiple switch:switch (expression ){case constante-1:liste d’instructions 1break;case constante-2:liste d’instructions 2break;case constante-3:liste d’instructions 3break;<strong>de</strong>fault:liste d’instructions <strong>de</strong>fautbreak;}■ Branchement non conditionnel: break, continue■ Branchement à ne pas utiliser: goto- p. 36/81


Les fonctionsintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctions● Les fonctions● Récursivité● Portée <strong>de</strong>s variablesLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ On peut en C découper un programme en plusieursfonctions.■ Seule la fonction main est obligatoire.■ Même si vous ne définissez pas <strong>de</strong> fonction, vous utilisez lesfonctions <strong>de</strong>s biblothèques C standard (return, printfpar exemple)■ Définition <strong>de</strong> fonction:type nom (type-1 arg-1,...,type-n arg-n){[déclarations <strong>de</strong> variables locales ]liste d’instructions}int factorielle(int n){int i, fact;for (i = 1,fact=1; i


Imbrication <strong>de</strong> fonctionsintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctions● Les fonctions● Récursivité● Portée <strong>de</strong>s variablesLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ En C on ne peut pas définir une fonction à l’intérieur d’unefonction■ En revanche on peut utiliser une fonction dans une fonction.■ Pour cela il y a <strong>de</strong>ux contraintes:1. Au moment <strong>de</strong> la compilation, lorsque le compilateurrencontre l’appel à une fonction factorielle, il faut qu’ilai déjà rencontré l’en-tète <strong>de</strong> la fonction intfactorielle(int n)2. Au moment <strong>de</strong> l’édition <strong>de</strong> lien, il faut que l’un <strong>de</strong>s co<strong>de</strong>sobjet contienne le co<strong>de</strong> compilé <strong>de</strong> la fonction factorielle.■ On a plusieurs moyens pour assurer ces contraintes:1. Un seul fichier2. Déclarer les en-têtes <strong>de</strong> fonctions en début <strong>de</strong> fichier3. Compilation séparée- p. 39/81Fonctions dans Un seul fichierintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctions● Les fonctions● Récursivité● Portée <strong>de</strong>s variablesLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C//fonction factorielle//calcule n! ou n entierint factorielle(int n){int i, fact;//double initialisationfor (i = 1,fact=1; i


Fonction avec déclaration <strong>de</strong>s en-têtes//Declaration en-tetesint factorielle(int n);intro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctions● Les fonctions● Récursivité● Portée <strong>de</strong>s variablesLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C//fonction main//affiche 10! à l’ecranint main(){int x;x=factorielle(10);printf("10!=%d\n",x);return(0);}//fonction factorielle//calcule n! ou n entierint factorielle(int n){int i, fact;//double initialisationfor (i = 1,fact=1; i


Fonctions: La bonne manière <strong>de</strong> faire//fichier fact3.hintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctions● Les fonctions● Récursivité● Portée <strong>de</strong>s variablesLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C//fichier fact3.c//fonction factorielle//calcule n! ou n entierint factorielle(int n){int i, fact;//double initialisationfor (i = 1,fact=1; i0//<strong>de</strong> manière récursiveint factRecurs(int n){int fact;if (n==1) //condition d’arretfact=1;elsefact=n*factRecurs(n-1);return(fact);}- p. 44/81


Récursivitéintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctions● Les fonctions● Récursivité● Portée <strong>de</strong>s variablesLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ La récursivité est très importante dans certains paradigmes<strong>de</strong> programmation (programmation fonctionnelle).■ Elle correspond à une métho<strong>de</strong> naturelle <strong>de</strong> décompositiond’un problème en problèmes plus simple:◆ pour calculer n!, je cacule (n − 1)! (plus simple)◆ puis je calcule n ∗ (n − 1)!■ Pour s’assurer que. que le programme ne va pas bouclerindéfiniement, il est impératif <strong>de</strong>;◆ Définir la condition d’arret: ici c’est n==1◆ Définir une quantité qui va croître (ou décroître) lors <strong>de</strong>sappels successifs <strong>de</strong> la fonction jusqu’à ce que lacondition d’arret soit vérifiée, ici cette quantitée est n lavaleur <strong>du</strong> paramètre.◆ On peut formaliser cela avec la notion d’invariant- p. 45/81Portée <strong>de</strong>s variableintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctions● Les fonctions● Récursivité● Portée <strong>de</strong>s variablesLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Les variables manipulées dans un programme C ne sont pastoutes traitées <strong>de</strong> la même manière. En particulier, ellesn’ont pas toutes la même <strong>du</strong>rée <strong>de</strong> vie. On distingue <strong>de</strong>uxcatégories <strong>de</strong> variables.◆ Les variables permanentes (ou statiques)◆ Les variables temporaires■ Chaque variable déclarée a une portée (ou <strong>du</strong>rée <strong>de</strong> vie) quiest la portion <strong>de</strong> co<strong>de</strong> dans laquelle elle est connue.■ On peut déclarer <strong>de</strong>s variables au début <strong>de</strong> chaque bloc(début d’une fonction ou portion <strong>de</strong> co<strong>de</strong> entre accola<strong>de</strong>). Laportée (ou <strong>du</strong>rée <strong>de</strong> vie) <strong>de</strong> ces variables est limitée au bloc.■ Les blocs sont forcément imbriqués lexicalement, lors d’uneutilisation d’une variable n, elle peut avoir été déclarée <strong>de</strong>uxfois dans la suite <strong>de</strong>s blocs englobant. L’utilisationcorrespond à celle <strong>de</strong> la première définition rencontréelorsque l’on remonte dans les blocs (i.e. la <strong>de</strong>rnièreeffectuée temporellement).- p. 46/81


Portée: exempleintro<strong>du</strong>ctionLes bases <strong>du</strong> Cint n = 10;void fonction();Les fonctions● Les fonctions● Récursivité● Portée <strong>de</strong>s variablesLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en Cvoid fonction(){int n = 0;n++;printf("appel numero %d\n",n);return;}main(){int i;for (i = 0; i < 5; i++)fonction();}----------------appel numero 1appel numero 1appel numero 1appel numero 1appel numero 1Portée: exemple- p. 47/81intro<strong>du</strong>ctionLes bases <strong>du</strong> Cint n;void fonction();Les fonctions● Les fonctions● Récursivité● Portée <strong>de</strong>s variablesLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsvoid fonction(){ n++;printf("appel numero %d\n",n);return;}Erreurs courante en Cmain(){ int i;for (i = 0; i < 5; i++)fonction();}-----------------appel numero 1appel numero 2appel numero 3appel numero 4appel numero 5- p. 48/81


Les entrées-sortiesintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ La librairie standard libstdio.a propose <strong>de</strong>s fonctionspour faire <strong>de</strong>s entrées-sorties sur les périphériquesstandard: l’écran et le clavier.■ Ces fonctions sont printf pour écrire et scanf pour lire■ Il faut inclure la directive #inclu<strong>de</strong> au début<strong>du</strong> fichier si on désire les utiliser.■ Ce sont <strong>de</strong>s fonctions d’impression formatée, ce qui signifieque les données sont converties selon le format particulierchoisi.- p. 49/81La fonction printfintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ La syntaxe <strong>de</strong> la fonction printf est:printf("chaîne <strong>de</strong> contrôle ",expr-1, ..., expr-n);■ La "chaîne <strong>de</strong> contrôle" contient le texte à afficher etles spécifications <strong>de</strong> format correspondant à chaqueexpression à afficher.■ %d indique l’affichage d’un entier signé en décimal.■ %u indique l’affichage d’un entier non signé en décimal.■ %c indique l’affichage d’un caractère.■ %f indique l’affichage d’un réel (double) en décimale.■ exemples:int a;a=10;printf("a vaut %d \n",a);■ résultats:a vaut 10 a vaut 10int a;a=10;printf("a vaut %4d \n",a);- p. 50/81


printf: exemplesintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ %x indique l’affichage d’un entier non signé en hexadécimal.■ exemples:int a;a=10;printf("a vaut (en hexa) %x \n",a);■ résultats:a vaut (en hexa) A a vaut 10■ Attention ! Il y a une conversion <strong>de</strong> type:■ exemples:char a;a=66;//conversion en intprintf("a vaut %d \n",a);■ résultats:a vaut 66short a;a=10;//conversion en intprintf("a vaut %d \n",a);short a;a=66;printf("a vaut %c \n",a);a vaut B- p. 51/81Encore printfintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ exemples: %f, %edouble x = 1e-8 + 1000;printf("x vaut %f \n",a);■ résultats:x vaut 1000.000000■ exemples: (conversion vers unsigned)int a;a=-23674;;printf("a vaut %d \n",a);■ résultats:double x = 1e-8 + 1000;printf("x vaut %e \n",a);x vaut 1.000000e+03int a;a=-23674;;//conversion en unsignedprintf("a vaut %u \n",a);a vaut -23674 a vaut 4294943622- p. 52/81


Encore printfintro<strong>du</strong>ctionLes bases <strong>du</strong> C■ programme:#inclu<strong>de</strong> Les fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en Cint main(){fprintf(stdout,"Ascii[%d]=%c, en octal: %o en hexa: %x\n",’\101’,’\101’,’\101’,’\101’);fprintf(stdout,"Ascii[%d]=%c, en octal: %o en hexa: %x\n",65,65,65,65);return(0);}■ résultat:trisset@hom:~/<strong>cours</strong>/2005/AGP/<strong>cours</strong>_tri/transp$ exCharAscii[65]=A, en octal: 101 en hexa: 41Ascii[65]=A, en octal: 101 en hexa: 41trisset@hom:~/<strong>cours</strong>/2005/AGP/<strong>cours</strong>_tri/transp$- p. 53/81Attention aux chaines!intro<strong>du</strong>ctionLes bases <strong>du</strong> C■ programme:#inclu<strong>de</strong> Les fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsint main(){int i;char chaine[4]={’\101’,’\101’,’\101’,’\0’};char fausseChaine[3]={’\101’,’\101’,’\101’};Erreurs courante en Cfprintf(stdout,"chaine=%s,\n",chaine);fprintf(stdout,"fausseChaine=%s,\n",fausseChaine);return(0);}■ résultat:trisset@hom:~/<strong>cours</strong>/2005/AGP/<strong>cours</strong>_tri/transp$ exChar2chaine=AAA,fausseChaine=AAA·öÿ¨öÿ¿;


La fonction scanfintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ La syntaxe <strong>de</strong> la fonction scanf est:scanf("chaîne <strong>de</strong> contrôle ",expr-1, ..., expr-n);■ Ici, la "chaîne <strong>de</strong> contrôle" ne contient que les formats■ Les données à entrer au clavier doivent être séparées par <strong>de</strong>s blancs ou<strong>de</strong>s sauf s’il s’agit <strong>de</strong> caractères ( est un caractère).■ Les formats sont légèrement éten<strong>du</strong>s par rapport à ceux <strong>de</strong> printf■ exemple:#inclu<strong>de</strong> main(){int i;printf("entrez un entier sous forme hexa<strong>de</strong>cimale i = ");scanf("%x",&i);printf("i = %d\n",i);}■ Si on entre au clavier la valeur 1a, le programme affiche i = 26.■ Attention à bien donner l’adresse <strong>de</strong> la variable à affecter.- p. 55/81Passage <strong>de</strong> paramêtre par référenceintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Tout se passe comme si la fonction scanf modifiait un <strong>de</strong>ses argument.■ En fait comme les argument sont passé par valeurs, on doitpasser en paramêtre un pointeur sur l’objet à modifier (doncpasser l’adresse <strong>de</strong> l’objet)■ La fonction scanf ne peut modifier son argument, mais ellepeut modifier l’objet pointé par l’argument.■ Ce mechanisme est utilisé systématiquement en C, pour quela fonction modifie un objet, il est passé en argument parréférence.- p. 56/81


Fichiersintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Les accès à un fichier se font par l’intermédiaire d’un tampon(buffer) qui permet <strong>de</strong> ré<strong>du</strong>ire le nombre d’accès auxpériphériques (disque...).■ Pour pouvoir manipuler un fichier, un programme a besoind’un certain nombre d’informations : l’adresse <strong>du</strong> tampon,position dans le fichier, mo<strong>de</strong> d’accès (lecture ou écriture) ...■ Ces informations sont rassemblées dans une structure dontle type, FILE *, est défini dans stdio.h. Un objet <strong>de</strong> typeFILE * est un stream (flot).■ Avant <strong>de</strong> lire ou d’écrire dans un fichier, on l’ouvre par lacomman<strong>de</strong> fich=fopen("nom-<strong>de</strong>-fichier","r").Cette fonction dialogueavec le système d’exploitation et initialise un stream fich,qui sera ensuite utilisé lors <strong>de</strong> l’écriture ou <strong>de</strong> la lecture.■ Après les traitements, on ferme le fichier grâce à la fonctionfclose(fich).- p. 57/81Fichiersintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ on peut ouvrir un fichier sous plusieurs mo<strong>de</strong>s: lecture ("r"), écriture au début ("w"),écriture à la fin ("a"). fopen retourne 0 en cas d’echec.■ Exemple:FILE *fich;fich=fopen("./monFichier.txt");if (!fich) fprintf(st<strong>de</strong>rr,"Erreur d’ouverture : %s\n","./monFichier.txt");■ Un objet <strong>de</strong> type FILE est quelquefois appelé un déscripteur <strong>de</strong> fichier, c’est un entierdésignant quel est le fichier manipulé.■ Trois <strong>de</strong>scripteurs <strong>de</strong> fichier peuvent être utilisés sans qu’il soit nécessaire <strong>de</strong> les ouvrir(à condition d’utiliser stdio.h):◆ stdin (standard input) : unité d’entrée (par défaut, le clavier, valeur <strong>du</strong><strong>de</strong>scripteur: 1) ;◆ stdout (standard output) : unité <strong>de</strong> sortie (par défaut, l’écran, valeur <strong>du</strong><strong>de</strong>scripteur: 0) ;◆ st<strong>de</strong>rr (standard error) : unité d’affichage <strong>de</strong>s messages d’erreur (par défaut,l’écran, valeur <strong>du</strong> <strong>de</strong>scripteur: 2).■ Il est fortement conseillé d’afficher systématiquement les messages d’erreur sur st<strong>de</strong>rrafin que ces messages apparaissent à l’écran même lorsque la sortie standard estredirigée.- p. 58/81


Autres fonction <strong>de</strong> lecture/ecritureintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Entrée/sorties <strong>de</strong> caractères◆ int fgetc(FILE* flot);◆ int fputc(int caractere, FILE *flot)■ Entrée/sorties <strong>de</strong> chaînes <strong>de</strong> caractères◆ char *fgets(char *chaine, int taille, FILE* flot);◆ int fputs(const char *chaine, FILE *flot)■ Entrée/sorties binaires◆ size_t fread(void *pointeur, size_t taille, size_t nombre,FILE *flot);◆ size_t fwrite(void *pointeur, size_t taille, size_t nombre,FILE *flot);■ positionnement dans un fichier◆ int fseek(FILE *flot, long <strong>de</strong>placement, int origine);◆ trois valeurs possibles pour origine: SEEK_SET (égale à 0) : début <strong>du</strong> fichier,SEEK_CUR : position courante, SEEK_END (égale à 2) : fin <strong>du</strong> fichier.- p. 59/81fgetc, fputc: exempleintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C#inclu<strong>de</strong> #inclu<strong>de</strong> #<strong>de</strong>fine ENTREE "entree.txt"#<strong>de</strong>fine SORTIE "sortie.txt"int main(void){FILE *f_in, *f_out;int c;}if ((f_in = fopen(ENTREE,"r")) == NULL){fprintf(st<strong>de</strong>rr, "\nErreur: Impossible <strong>de</strong> lire le fichier %s\n",ENTREE);return(EXIT_FAILURE);}if ((f_out = fopen(SORTIE,"w")) == NULL){fprintf(st<strong>de</strong>rr, "\nErreur: Impossible d’ecrire dans le fichier %s\n",SORTIE);return(EXIT_FAILURE);}while ((c = fgetc(f_in)) != EOF)fputc(c, f_out);fclose(f_in);fclose(f_out);return(EXIT_SUCCESS);- p. 60/81


Arguments <strong>de</strong> la fonction mainintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ La fonction main doit être présente si le programme estutilisé directement (pas comme une librairie), par exemple:appelé <strong>de</strong>puis le shell.■ En général, la fonction main retourne un co<strong>de</strong> d’erreur <strong>de</strong>type int.■ Lorsque l’on compile avec la comman<strong>de</strong> gcc monProg.c-o monProg, l’exécution <strong>de</strong> la command monProg dans unshell appelle la fonction main■ Si on lance la comman<strong>de</strong> monProg avec <strong>de</strong>s arguments (ex:monProg fichier1.txt, il est possible <strong>de</strong> récupérer dansla fonction main la valeur <strong>de</strong> ces arguments sous forme <strong>de</strong>chaînes <strong>de</strong> caractères: on utilise les arguments standard <strong>de</strong>la fonction main: int argc (argument count), char*argv[] (argument values) (on peut aussi récuperer <strong>de</strong>svariables d’environnement grâce à envp)- p. 61/81Exemple <strong>de</strong> fonction mainintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Multiplication <strong>de</strong> <strong>de</strong>ux entier: gcc mult.c -o multshell> mult 8 32Le pro<strong>du</strong>it <strong>de</strong> 8 par 32 vaut: 256#inclu<strong>de</strong> #inclu<strong>de</strong> int main(int argc, char *argv[]){int a, b;if (argc != 3){printf("\nErreur : nombre invali<strong>de</strong> d’arguments");printf("\nUsage: %s int int\n",argv[0]);return(EXIT_FAILURE);}a = atoi(argv[1]);b = atoi(argv[2]);printf("\nLe pro<strong>du</strong>it <strong>de</strong> %d par %d vaut : %d\n", a, b, a * b);return(EXIT_SUCCESS);}- p. 62/81


Convention d’écriture en Cintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties● Les entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Il existe très peu <strong>de</strong> contraintes dans l’écriture d’unprogramme C. Toutefois ne prendre aucune précautionaboutirait à <strong>de</strong>s programmes illisibles.■ On n’écrit qu’une seule instruction par ligne : le point virguled’une instruction ou d’une déclaration est toujours le <strong>de</strong>rniercaractère <strong>de</strong> la ligne.■ Les instructions sont disposées <strong>de</strong> telle façon que lastructure mo<strong>du</strong>laire <strong>du</strong> programme soit mise en évi<strong>de</strong>nce.◆ une accola<strong>de</strong> ouvrante marquant le début d’un bloc doitêtre seule sur sa ligne ou placée à la fin d’une ligne.◆ Une accola<strong>de</strong> fermante est toujours seule sur sa ligne.■ Les instructions doivent être in<strong>de</strong>ntées afin que toutes lesinstructions d’un même bloc soient alignées. Le mieux estd’utiliser le mo<strong>de</strong> C d’emacs ou <strong>de</strong> vi.■ On commente abondament le co<strong>de</strong>- p. 63/81Planintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ction■ Pointeurs <strong>de</strong> fonctions■ Les erreurs courantes en C (sourcehttp://nicolasj.<strong>de</strong>veloppez.com/articles/erreurs/par exemple)Pointeur <strong>de</strong> fonctionsErreurs courante en C- p. 64/81


Utilité <strong>de</strong>s pointeurs <strong>de</strong> fonctionintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Mécanismes dynamiques◆ plug-in◆ Modifier une fonctionnalité sans arrêter le programme◆ ajouter <strong>de</strong> nouvelles fonctionnalités■ Exemple: fonction <strong>de</strong> décodage <strong>de</strong> trame niveau 2:dépendant <strong>de</strong> l’interface connectée (ethernet, wifi, etc.)- p. 65/81Un premier exempleintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C#inclu<strong>de</strong> #inclu<strong>de</strong> //<strong>de</strong>claration <strong>de</strong> fonctionint fonct1(int a){fprintf(stdout,"Je suis fonct1(%d)\n",a);return(0);}int main(){// <strong>de</strong>claration <strong>de</strong> pointeur <strong>de</strong> fonctionint (*foncPtr)(int a);foncPtr=&fonct1;(*foncPtr)(10);return(0);}- p. 66/81


Comprendre les déclarationsintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Déclaration d’une variable: int *q[3]◆ [] plus prioritaire que *, donc:int *q[3] ⇔ int (*(q[3]))◆ l’expression (*(q[3])) est <strong>de</strong> type int◆ l’expression q[3] est <strong>de</strong> type pointeur vers un int◆ l’expression (i.e. la variable) q est <strong>de</strong> type tableau <strong>de</strong>pointeur vers un int■ Déclaration d’une fonction:int fonct1(int a)◆ l’expression fonct1(int a) est <strong>de</strong> type int◆ l’expression (i.e. la variable) fonct1 est <strong>de</strong> type fonctionqui prend un int et renvoie un int◆ Les parenthèses après un symbole indique que lesymbole est une fonction (<strong>de</strong> même que les crochetsaprès un symbole indique que le symbole est un tableau).- p. 67/81Déclaration d’un pointeur <strong>de</strong> fonctionintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Déclaration d’un pointeur <strong>de</strong> fonction:int (*foncPtr)(int a)◆ l’expression (*foncPtr)(int a) est <strong>de</strong> type int◆ l’expression (*foncPtr) est <strong>de</strong> type fonction qui pren<strong>du</strong>n int est renvoie un int◆ l’expression (i.e. la variable) foncPtr est <strong>de</strong> type pointeurvers une fonction qui prend un int et renvoie un int■ lors <strong>de</strong> l’utilisation, (presque) tout se passe comme si lafonction était une Lvalue:◆ On peut affecter une adresse <strong>de</strong> fonction au pointeur <strong>de</strong>fonction: foncPtr=&fonct1;◆ Si on déréférence le pointeur <strong>de</strong> fonction, on obtient unefonction: l’exécution <strong>de</strong> (*foncPtr)(10); affiche:Je suis la fonction fonct1(10)- p. 68/81


En fait, c’est un peu plus compliqué...intro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ En C, une fonction est automatiquement castée en pointeur<strong>de</strong> fonction (et inversement):foncPtr=&fonct1 ⇔ foncPtr=fonct1(*foncPtr)(10); ⇔ (foncPtr)(10)■ Tout comme pour les tableaux:tab ⇔ &tab■ Pour les fonctions et les tableaux qui ne sont pas <strong>de</strong>sL-values (on les appelle quelquefois <strong>de</strong>s labels) lecompilateur i<strong>de</strong>ntifie a et &a■ On peut donc écrire:int (*foncPtr)(int a);foncPtr=fonct1;foncPtr(10);- p. 69/81On peut donc ecrire:intro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C#inclu<strong>de</strong> #inclu<strong>de</strong> //<strong>de</strong>claration <strong>de</strong> fonctionint fonct1(int a){fprintf(stdout,"Je suis fonct1(%d)\n",a);return(0);}int main(){// <strong>de</strong>claration <strong>de</strong> pointeur <strong>de</strong> fonctionint (*foncPtr)(int a);foncPtr=fonct1;foncPtr(10);return(0);}- p. 70/81


Un autre exempleintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sorties//comparaison <strong>de</strong> <strong>de</strong>ux entiersint main(void){int i,t[6]={1,5,2,3,6,4};Intro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en Cint croissant(int i, int j){if (i


Passage <strong>de</strong> fonction par référenceintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Comme pour une variable normale, on peut modifier unpointeur <strong>de</strong> fonction en le passant en paramêtre parréférénce.■ Pour avoir une fonction qui modifie un pointeur <strong>de</strong> fonction(i.e. qui modifie la qui fonction appelée lorsque le pointeurest invoqué), il faut que son paramêtre soit un pointeur surun pointeur <strong>de</strong> fonction.- p. 73/81Passage <strong>de</strong> fonction par référenceintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en CchangeOrdre(int (**fcomp1)(int, int), int (*fcomp2)(int, int)){*fcomp1=fcomp2;}int main(void){int i,t[6]={1,5,2,3,6,4};int (*fcomp)(int,int);fcomp=croissant;trie(t, 6, fcomp);for(i=0;i


intro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en CLes erreurs courantes en C- p. 75/81Confusion entre == et =intro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ction■ À ne pas faire:if (size = 0) ....■ Détection: l’option -Wall <strong>du</strong> compilateur avertit leprogrammeur (warning)Pointeur <strong>de</strong> fonctionsErreurs courante en C- p. 76/81


Confusion entre opérateurs logiques et binairesintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Le ET logique (&&) qui retourne 0 ou 1 (en s’arrêtant aupremier argument s’il est faux)■ Le ET binaire (&) évalue ses <strong>de</strong>ux opéran<strong>de</strong>s et effectue leET bit à bit entre ses <strong>de</strong>ux opéran<strong>de</strong>s.■ Le OU logique (||) qui retourne 0 ou 1 (en s’arrêtant aupremier argument s’il est vrai)■ Le OU binaire (|) évalue ses <strong>de</strong>ux opéran<strong>de</strong>s et effectue leOU bit à bit entre ses <strong>de</strong>ux opéran<strong>de</strong>s.■ Impossible à détecter à la compilation.- p. 77/81Problèmes <strong>de</strong> macrosintro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ On n’écrit pas#<strong>de</strong>fine MAX 10;◆ A[MAX] <strong>de</strong>vient A[10;]■ On n’écrit pas#<strong>de</strong>fine MAX=10◆ Erreur détectée à la compilation, mais lors <strong>de</strong> l’utilisation<strong>de</strong> MAX (la ligne référencée n’est pas celle <strong>de</strong> la définition<strong>de</strong> MAX).■ On écrit#<strong>de</strong>fine MAX 10■ En cas <strong>de</strong> doute, on peut utiliser gcc -E pour vérifierl’expansion correcte <strong>de</strong>s macros.- p. 78/81


Fonctions retournant un caractère getc...intro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en Cchar c;while ( (c = getchar ()) != EOF)...■ La fonction getchar retourne un entier■ Les cast implicites effectués sont:while ( (int)(c = (char)getchar ()) != EOF)■ le caractère EOF (qui marque la fin d’un fichier : End Of File)est un caractère invali<strong>de</strong> généralement égal à -1 mais il peutparfaitement être égal à 128, dans ce cas on dépasse lacapacité <strong>de</strong> stockage d’un char et l’on se retrouve avec unrésultat égal à -128 : la condition <strong>du</strong> while sera toujoursfausse, le programme boucle indéfiniment!■ Il faut écrire:int cInt;char c;while ( (cInt = getchar ()) != EOF){c=(char)cInt;...Erreurs avec if et for- p. 79/81intro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ point-virgule mal placéif (a < b) ;a = b;■ Le mauvais elseif (a < b)if (b < c) then b = c;elseb = a;■ Ce qu’il fallait faire:if (a < b){ if (b < c) then b = c; }elseb = a;for (i=0; i


Et les plus courantes...intro<strong>du</strong>ctionLes bases <strong>du</strong> CLes fonctionsLes entrées-sortiesIntro<strong>du</strong>ctionPointeur <strong>de</strong> fonctionsErreurs courante en C■ Mauvaise in<strong>de</strong>ntation■ Pas <strong>de</strong> makefile (ou pas <strong>de</strong> cible clean dans le makefile)■ exemple <strong>de</strong> fichier configuration vi:syntax on" coloration syntaxiqueset autoin<strong>de</strong>nt " i<strong>de</strong>ntationset cin<strong>de</strong>nt " pour Cset nopasteset ts=4 " tabulation a 4 caracteresset sw=4■ Sous vi:◆ == pour in<strong>de</strong>nter la ligne courante,◆ =G pour i<strong>de</strong>nter tout le fichier:- p. 81/81

Hooray! Your file is uploaded and ready to be published.

Saved successfully!

Ooh no, something went wrong!