0% ont trouvé ce document utile (0 vote)
28 vues31 pages

Introduction au Langage C et Ses Concepts

Ce document décrit le langage de programmation C. Il présente les principales caractéristiques du langage ainsi que les différents types de base, instructions, entrées-sorties, déclarations, fonctions et compilation en C.

Transféré par

Perrait Dji
Copyright
© © All Rights Reserved
Nous prenons très au sérieux les droits relatifs au contenu. Si vous pensez qu’il s’agit de votre contenu, signalez une atteinte au droit d’auteur ici.
Formats disponibles
Téléchargez aux formats PDF, TXT ou lisez en ligne sur Scribd
0% ont trouvé ce document utile (0 vote)
28 vues31 pages

Introduction au Langage C et Ses Concepts

Ce document décrit le langage de programmation C. Il présente les principales caractéristiques du langage ainsi que les différents types de base, instructions, entrées-sorties, déclarations, fonctions et compilation en C.

Transféré par

Perrait Dji
Copyright
© © All Rights Reserved
Nous prenons très au sérieux les droits relatifs au contenu. Si vous pensez qu’il s’agit de votre contenu, signalez une atteinte au droit d’auteur ici.
Formats disponibles
Téléchargez aux formats PDF, TXT ou lisez en ligne sur Scribd

Langage C

SOMMAIRE
.1 Généralités .......................................................................................................................... 2
.2 types de base....................................................................................................................... 3
.3 Instructions ......................................................................................................................... 4
.3.1 Affectation / Expressions ........................................................................................... 4
.3.2 Instructions de sélection ............................................................................................. 6
.3.3 Instructions de répétition ............................................................................................ 7
.3.4 Autres instructions...................................................................................................... 8
.4 Entrées – Sorties bufférisées ............................................................................................ 10
.4.1 Entrées-Sorties non formatées .................................................................................. 10
.4.2 Entrées-Sorties formatées ......................................................................................... 10
.5 Déclaration – Allocation mémoire ................................................................................... 13
.5.1 Classes d’allocation .................................................................................................. 13
.5.1.1 Variables extérieures aux fonctions ................................................................. 13
.5.1.2 Variables déclarées dans une fonction ............................................................. 13
.5.1.3 Déclaration de fonctions................................................................................... 14
.5.1.4 Classe d’allocation registre .............................................................................. 14
.5.2 Les objets structurés ................................................................................................. 14
.5.2.1 Tableaux ........................................................................................................... 14
.5.2.2 Les structures .................................................................................................... 15
.5.2.3 Les unions ........................................................................................................ 15
.5.2.4 Définition de type (création de synonymes) .................................................... 16
.5.2.5 Les énumérations.............................................................................................. 16
.5.2.6 Les pointeurs .................................................................................................... 16
.6 Conversion de types : coercion ........................................................................................ 18
.7 Allocation dynamique de zones ....................................................................................... 18
.8 Les fonctions .................................................................................................................... 19
.8.1 Définition ................................................................................................................. 19
.8.2 Fonctions récursives ................................................................................................. 20
.8.3 Les pointeurs sur les fonctions ................................................................................. 20
.8.3.1 Affectation de fonctions ................................................................................... 20
.8.3.2 Tableau de fonctions ........................................................................................ 21
.8.3.3 Passage de fonctions en arguments de fonctions ............................................. 21
.9 Récupération des arguments d'une commande................................................................. 21
.10 La compilation.............................................................................................................. 22
.10.1 Compilation et edition de liens sous UNIX ............................................................. 22
.10.2 Le pré-compilateur C ............................................................................................... 23
.10.2.1 Inclusion de fichiers ......................................................................................... 23
.10.2.2 Macro – definition ............................................................................................ 23
.10.2.3 Compilation conditionnelle .............................................................................. 24
.11 Manipulation de Fichiers .............................................................................................. 26
.11.1 Ouverture/Fermeture d’un fichier ............................................................................ 26
.11.2 Lecture/Ecriture octet par octet ................................................................................ 27
.11.3 Déplacement du pointeur ......................................................................................... 28
.11.4 Lecture/Ecriture d’objets quelconques ..................................................................... 29
.11.5 Lectures/Ecritures formatées .................................................................................... 29
.11.6 Lectures/Ecritures de chaînes de caractères ............................................................. 30
.11.7 Compléments sur le paramètre mode passé à fopen ................................................ 30

Professeur: ASSALE Adjé Louis 1/31 INP-HB


Langage C

LE LANGAGE C
.1 Généralités

Langage créé pour le développement du système UNIX (écrit en 98% en C).

Le caractéristiques sont :
 Langage structuré : pas de goto, typé c’est-à-dire déclaration
obligatoire (mais laxisme au niveau de la vérification.
 Langage d’un niveau moyen
 Langage permettant la manipulation d’objets très élémentaires
proche de l’architecture des processus :
- décalage de chaînes de bits
- accès aux registres

Structure générale d’une application C :

Inclusion de fichier : #include<fichier.h>

Déclaration de variables globales

Définitions de fonctions : éventuellement récursives et


partageant les variables globales.

- une fonction et une seule s’appelle main()


main()
{ printf("bonjour") ;}

- les fonctions et variables peuvent être réparties dans plusieurs fichiers


- la compilation comporte 3 phases

code C code assemblage binaire

fichier.c temporaire fichier.s exe


pré-processeur compilation assemblage

Professeur: ASSALE Adjé Louis 2/31 INP-HB


Langage C

Exemple de programme en C
bonjour.c
#include<stdio.h>

void main()
{
printf("Bonjour les amis");
}

Le pré-processeur traite les lignes commençant par #

#define - définition de macros et de constantes


#include - inclusion de fichiers

#if
#else
#endif - compilation conditionnelle
#ifdef
#ifndef

#undef - suppression de définition

- format d’écriture de programme : libre


- commentaires : /* chaînes quelconques sans commentaires */
- identificateurs : commencent par une lettre (le caractère ‘_’ est une lettre), la
casse est respectée (majuscule  minuscule). Convention :
constantes en majuscule – variables en minuscule
- mots-clés : en minuscules et réservés

.2 types de base

- entiers : unsigned, int, short, long


exemple: int x,y; short u ; unsigned z ;
les opérateurs : +, -, *, / (division entière), % (modulo)

- réels : float, double


exemple : float x, y ;
les opérateurs : +, -, *, /

Professeur: ASSALE Adjé Louis 3/31 INP-HB


Langage C

- caractères : char
exemple : char c ; ‘a’ notation
les caractères particuliers : ‘\n’ newline, ‘\t’ tab, ‘\0’ NULL, ‘\\’ \, ‘\b’
backspace, ‘\r’ return, ‘\f’ formfeed ou clear screen, ‘\’’ ‘, ‘\"’ ".

- chaînes de caractères : pas de type spécifique pour les chaînes de caractères


mais un pointeur sur un caractère : char *s.
représentation interne "abc"  |a|b|c|\0|
"x"  |x|\0|  ‘x’  |x| 0 1 2 3

- booléen : pas de type : 0, NULL est faux le reste est vrai.

Conversion automatique entre les types char, int, et float.

int x ; char c ;
c = ’a’ +1 ; /* c  ’b’ */
x = c; /* x  66 */
c = x+2; /* c  ‘d’ */

Définition de constantes

#define PI 3.14
#define EOL ‘\n’
#define ERR1 "Code inconnu \n"

const type identificateur = valeur exemple : const float PI = 3.14

.3 Instructions

.3.1 Affectation / Expressions

 Opérateurs d’affectation

= opérateur d’affectation
Exemple : i = 2*j+3 ;

= affectation multiple
Exemple: i=7+ (j=3);
f=g=h=9;

Professeur: ASSALE Adjé Louis 4/31 INP-HB


Langage C

op= raccourcis d’affectation


i+ = 5 ; <=> i = i + 5;
i/ = 2; <=> i = i/2;

 incrémentation / décrémentation

++ incrémentation ++i <=> i = i+1


-- decrémentation i++ <=> (i=i+1)-1
(j = i++ <=> j=i; i++;)
(j = ++i <=> i++; j = i;)

exemple:
i = 2;
j = 2*i++;
k = 2*++i;

Quels sont les valeurs de j, i après post et pré incrémentation et de k;

 Opérateurs logiques

= = égalité
Exemple : if (x==0)
!= non égal
Exemple : (x !=y)

<=, <, >=, > inférieur et supérieur

! négation
&& Et logique
|| Ou logique

 Opérateurs sur les bits

~ négation bit à bit


& Et bit à bit
| Ou bit à bit
^ Ou exclusif bit à bit (Xor)
<<, >> décalage à gauche et à droite

 Opérateurs sur pointeur

Professeur: ASSALE Adjé Louis 5/31 INP-HB


Langage C

* (exemple : *p) /* opérateur unaire fournissant la valeur stockée à */


/* l'adresse indiquée */

 (exemple :p date  (*p).date) /* opérateur d’accès au champ d’un


pointeur sur structure */

 autres

?: conditionnelle raccourci (exemple : y=(x>0)? x : -x;  |x|)

sizeof taille d’un type ou d’une variable (exemple :sizeof(int) ou sizeof(x))

 expression simple
Expression quelconque suivie de ; i++; x=*++p;

 expression composée

{ [déclarations locales]
suite d'instructions }
exemple:
{ int aux;
aux = i;
i = j;
j = aux;
}  obligatoire (;)
 pas de ;

.3.2 Instructions de sélection

 Sélection if:
if (<expression>)
<instruction>
[ else <instruction>]

if (i>0) i++; if (i>0) i++; else i++;


 obligatoire (;)

if (delta>0)
{ … }  pas de ;
else if (delta = = 0)
x = -b/(2*a);
else printf (" pas de raciness réelles\n");

Professeur: ASSALE Adjé Louis 6/31 INP-HB


Langage C

 Sélection switch
switch (<expression>)
{case <expression constante>: <liste d'instructions>

[default : <liste d'instructions>]
}

Si la valeur de l'expression est égale à l'une des expressions constantes on


exécute toutes les instructions des listes suivantes sinon on exécute la liste
default si elle présente.

char c;
switch (c)
{ case 'd' :
case 'c' : supprimer( ); break;
case 'i' : inserer( ); break;
case 'm' : modifier ( );break;
case 's' : sortir( ); break;
default : printf ("erreur code\n");
}

.3.3 Instructions de répétition

 répétition while: while (<expression>) <instruction> ;

Exemple: recopie de chaîne ('\0' fin de chaîne)


char a[40], b[40];
char *s = a, *r = b;

int i=0; while (*r++=*s++);


while (a[i]!='\0') ou  instruction
{ b[i]=s[i]; i++;} vide
b[i]='\0';

 répétition do while:
do
<instruction>
while (<expression>);

Professeur: ASSALE Adjé Louis 7/31 INP-HB


Langage C

do
i--;
while(i);

 répétition for:
for (<liste1>; <expression>; <liste2>) <instruction>;

- liste i : liste d'expression séparées par des virgules (,)


- tout est facultatif

exemples:
for (;;) boucle infinie
for(i=0; i<=n; i++)
for (i=0; i<=n; i++, j--)
for (l1;e;l2) <instruction>  while (e) {<instruction> l2}

.3.4 Autres instructions

 sortie break
permet une sortie immédiate de l'instruction for, while, do while ou switch
englobante.

Exemple:

#define MAXTAB 100


int t[MAXTAB], x, nb;
for (i=nb=0; i<MAXTAB; i++)
if (t[i]=x) break;
else if (t[i]<x) nb++;

 sortie exit(n)
termine l'exécution du programme et renvoie n au processus père
(0  n  255) après fermeture de tous les fichiers.
(exit(0) implicite en fin de programme)

 continue
passe à l'itération suivante d'un for, while ou do while (peu utilisé).

Professeur: ASSALE Adjé Louis 8/31 INP-HB


Langage C

LES OPERATEURS EN LANGAGE C

Opérateurs Opérateurs Opérateurs Opérateurs Opérateurs Opérateurs spéciaux: Opérateurs


arithmétiques d'affectation relationnels booléens sur les bits Adresses, tableaux, divers
structures, unions

+ = == ! ~ & ?:
- += != || >> * ,
* -= < && << [] sizeof
/ *= <= & . ( type )
% /= > |  ()
++ %= >= ^
-- >>=
<<=
&=
^=
|=

Professeur: ASSALE Adjé Louis 9/31 INP-HB


Langage C

.4 Entrées – Sorties bufférisées

Elles ne font partie du langage lui même. Il faut inclure la bibliothèque


correspondante #include <stdio.h>.

.4.1 Entrées-Sorties non formatées

getchar( ): fonction qui retourne – un caractère lu sur stdin (clavier) ou –EOF si


on est en fin de fichier.
- En général EOF=-1.
- ^D = fin de fichier au clavier.

putchar(c): écrit le caractère c sur le fichier stdout (écran).

Exemple: while (((c=getchar())!=EOF) && (c!=' '));

gets(buff, n): buff de type char * et n de type int; gets


– lit sur stdin une chaîne de p caractères (pn-1 si on rencontre un
'\n', p=n sinon)
– ajoute le caractère NULL ('\0')
– place le résultat dans le buffer buff (pointeur ou tableau) –
retourne buff ou EOF

puts(buff):
- buff doit être un pointeur sur une chaîne de caractère (se terminant par
'\0')
- puts écrit cette chaîne sur stdout (non compris le caractère '\0') et ajoute
un '\n'.

gets(buff, n)  fgets(buff, n, stdin)


puts(buff)  fputs(buff, stdout) qui ne rajoute pas '\n'

.4.2 Entrées-Sorties formatées

#include<stdio.h> en tête du programme.

- Sortie sur stdout


printf(format, e1, …, en)

Professeur: ASSALE Adjé Louis 10/31 INP-HB


Langage C

où format est une chaîne contenant des paramètres de conversion:


%d int
%e %f float
%s chaîne
%c char
%u unsigned
auxquels se substituent les valeurs des expressions.
Exemple:
x=1; y=1.5;
printf("ceci est un exemple \n x=%d \ny=%f\n", x,y);

ceci est un exemple


x=1
y=1.5

- Entrée sur stdin


scanf(format, v1, …, vn)
v1, …, vn sont des pointeurs obligatoirement
scanf("%d%d", &i, &j);
i et j reçoivent deux entiers lus sur stdin

règles:
- %c le caractère suivant;
- %i%f%s ignore tous les \t, \n, espace puis lit jusqu'à la rencontre d'un
- non numérique (%i%f)
- espace, \t, \n (%s)
- %* donnée ignorée
- %3d lit exactement un entier sur 2 caractères
- %1s lit le premier caractère non espace.
- scanf renvoie EOF si une erreur ou une fin de fichier est detectée au cours
de la lecture. EOF vaut en général –1.

Remarque: dans les formats de printf on peut insérer derrière %.

- cadrage à gauche
n impression dans une zone de n caractères (cadrage à droite implicite)
.m m 1ers caractères d'une chaîne ou m décimales pour un float
n.m combinaison des deux précédents.

Professeur: ASSALE Adjé Louis 11/31 INP-HB


Langage C

TABLEAU RECAPITULATIF DES PRINCIPALES


FONCTIONS D'E/S STANDARDS
Appel de la fonction Prototype Son rôle Commentaires
dans
char c; Lit un seul caractère tape au clavier - pas d'écho
E c = getch(); conio.h sans l'afficher. c est de type int ou char- pas de \n après
avoir entrer c
N char c; Lit le prochain caractère du flux - écho
c = getchar(); stdio.h d'entrée stdin - prise en compte
T de c après \n
char c; Idem à getch mais affichage du - écho
R c = getche(); conio.h caractère rentré - pas de \n
char ch[10]; Lit une chaîne depuis le flux d'entrée - écho, \n
E gets(ch); stdio.h stdin et la place dans ch. Fin de lecture - ch peut
après \n qui est remplacé dans ch par un comporter espace
E caractère nul '\0' et tab
scanf(format, stdio.h effectue des entrées formatées depuis - écho
S adr1,…,adrN); stdin. Les arguments passés après la - validation après
chaîne de format doivent être des \n. le \n est laissé
adresses dans le buffer
d'entrée

char c; conio.h Envoi un caractère à l'écran


S putch(c);
O char c; stdio.h sortie du caractère c sur l'écran - pas de retour
R putchar(c); chariot
T char ch[10]; stdio.h sortie d'une chaîne de caractères à - \n
I puts(s); l'écran avec retour chariot automatiquement
E puts("bonjour");
S printf(format, stdio.h Ecrit des sorties formatées dans le flux - pas de \n
arg1,…,argN); standard stdout automatiquement

Professeur: ASSALE Adjé Louis 12/31 INP-HB


Langage C

.5 Déclaration – Allocation mémoire

La syntaxe de déclaration d’un objet est :

[<classe d’allocation>] <type> <liste d’identificateurs>


extern initialisation
static dans certains cas
register

.5.1 Classes d’allocation

.5.1.1 Variables extérieures aux fonctions

int i,j = 3; /* globales à tous les fichiers */


static int k, f = 5; /* locales au fichier */
extern int x ; /* déclarée dans un autre fichier */

Ce sont des variables globales partagées par les fonctions qui ne les redéfinissent
pas et qui existent pendant toute la durée du programme.

exemple f1.c F2.c

int x ; extern int x ;


static int y=3 ; static int y = 4;
main() g()
{…} { int i; ...}
f() {…} h() {…}

.5.1.2 Variables déclarées dans une fonction

f (int x, int y) /* type des arguments de f */


{ char a, b=’c’ ; /* variables locales à f initialisées dans la pile à
chaque
… appel */
static float u=3.5; /* variable locale à f initialisée au premier appel */

}

- classe automatique: x, y, a, b sont allouées dans la pile à chaque appel, détruite


à chaque retour.
- classe statique : u allouée en zone statique

Professeur: ASSALE Adjé Louis 13/31 INP-HB


Langage C

.5.1.3 Déclaration de fonctions

f (char x, char y) /* implicitement la fonction f retourne une valeur


{ int z=1 ; …} entière ou ne retourne rien */

float g (float z) /* g retourne une valeur réelle */


{…}

La classe d’allocation des fonctions est la même que pour les variables

char h(char c) /* fonction globale à tous les fichiers */


{…}

static int f(char x, char y) /* fonction locale au fichier qui retourne


un
{ int z = 1; … } entire */

extern f( ); /* f et h fonctions définies dans un autre fichier; on ne


extern char h(); précise pas leurs paramètres; mais on indique leur type */

.5.1.4 Classe d’allocation registre

Exemple : main()
{ register int i,s ;
s = 0;
for (i = 1; i<=10000; i++) s = s +i;
printf(“%d \n”, s);}
Les variables automatiques (locales aux fonctions et non “static”) allouées dans
la pile en temps normal, et de type char, int, float ou "pointeur" peuvent être
déclarées register. Elles sont alors allouées si possible dans les registres
machine. Ce qui implique une diminution sensible du temps d'exécution
(réduction de moitié sur le type d'exemple).

.5.2 Les objets structurés

.5.2.1 Tableaux

[<allocation>] <type> <identificateur> [c1]...[cn]

Professeur: ASSALE Adjé Louis 14/31 INP-HB


Langage C

les ci sont des constantes entières

Exemples:
char t[10]; tableau de 10 caractères t[0] t[1] ... t[9]
int u[ ] = {6, 5, 7, 3};
 taille facultative si initialisé

float mat[9][15];
mat[i][j] = 3.5;

for(i = 1; i<=9; i++)


for(j = 1; j<=15; j++)
c[i][j] = a[i][j] + b[i][j];

int w[][2] = {{1,0},{0,1}};

En C un tableau est équivalent à un pointeur.

.5.2.2 Les structures

struct date {int jour, mois, an;};


struct date d1, d2, d3;
d1.jour = 4; d1.mois = 5;
d1 = d2;
 définition et déclaration simultanée
struct date {int j, m, a;} d1, d2;
 structures emboîtées
struct stage { char nom[40];
struct date debut, fin;} s, t[10];
Quels sont les types des objets suivants?
s.nom
s.nom[4]
s.debut.mois
t[3].debut
t[3].nom[0]

.5.2.3 Les unions

union objet
{ float r;
char t[4];

Professeur: ASSALE Adjé Louis 15/31 INP-HB


Langage C

short int i[2];


} x;
x référence une zone de quatre octets qui peut être indifféremment vue comme:
un réel x.r=3.5;
4 caractères x.t[3] = 'c';
2 entiers x.i[1] = 3;

.5.2.4 Définition de type (création de synonymes)

typedef struct date {int j, m, a;};


date x, y, z;
typedef int entier;
entier i, j, k;

.5.2.5 Les énumérations

enum jours {Lundi, Mardi, Mercredi, Jeudi, Vendredi, Samedi, Dimanche};


enum jours jr;

jr ne peut prendre que les valeurs Lundi, ..., Dimanche.


Mais en fait, les valeurs d'énumération sont manipulées comme des valeurs
entières représentant un code dont le sens est explicité par la valeur
correspondante de l'énumération. Par exemple le code 3 (Valeur entière 3)
correspond à la valeur de l'énumération Jeudi (0 pour Lundi et 6 pour
Dimanche).

.5.2.6 Les pointeurs

int i;
int t[20];
int *p; /* *p est un entier, p est un pointeur sur un entier */

p = &i; /* p contient l'adresse de i */


*p = 3;

"En C un tableau est équivalent à un pointeur"

Professeur: ASSALE Adjé Louis 16/31 INP-HB


Langage C

p = t; /* pointeur sur l'adresse du 1er élément du tableau t[20] */


p
0
t

19

Que désignent les objets *p, *t, p[0] et t[0]?


Quels sont les types de p et t?

int t[20]; /* réserve effectivement un tableau et fait pointer un pointeur t sur


le 1er élément */
t est un pointeur mais réservé uniquement au tableau déclaré.

int *p; /* ne réserve qu'un pointeur non initialisé */


p peut pointer sur n'importe quel entier.

 Arithmétique sur les pointeurs


Si p pointe sur un objet de type t, alors p+1 pointe sur l'objet suivant en
mémoire; il est incrémenté de la taille de l'objet pointé sizeof(t).

int t[20];
int *p = t;

A quoi correspondent les objets suivants: *p, *(p+3) et *p+3.

char *s;
s = "abcd"; /* s pointe sur le début d'une constante chaîne */
que désigne s[3] et *(s+3)?

 Tableaux de pointeurs
char * name[] = {"lundi", "mardi", "mercredi", "jeudi", "vendredi", "samedi",
"dimanche"};

Quel est le type de name[i]?

name
|l|u|n|d|i|\0
0

Que désignent les objets suivants:

Professeur: ASSALE Adjé Louis 17/31 INP-HB


Langage C

*name[0]
name[0][0]
**name
*name[1]
**(name + 1)
name[1][0]
*(name[0] + 1)
*(*name + 1)
name[0][1]

Remarque: char (*adr)[5]; /* pointeur sur un tableau de cinq char */

.6 Conversion de types : coercion

Il y a la conversion automatique de types entre: char, int et float.


Il est parfois nécessaire de forcer une conversion; la coercion de type.

Exemple1: transformation d'un pointeur sur un entier en un pointeur sur le


premier octet de cet entier et réciproquement.

int *p;
char *q;

q = (char *)p;
p = (int *)q;

Exemple2: transformation de pointeur quelconque en entier et vis versa.

int i, *p, (*pf)();

i = (int)p;
p = (int *)i;
i = (int)pf;
pf = ((int*)())i;

.7 Allocation dynamique de zones

Sert à réserver une zone mémoire pour les variables de type pointeur.

- p = malloc(n) : retourne un pointeur sur une zone de n octets contigus non


initialisés
- free(p) : libère la zone pointée par p sans la modifier

Professeur: ASSALE Adjé Louis 18/31 INP-HB


Langage C

- p = calloc(n,t): retourne un pointeur sur une zone de n objets de t octets


initialisés à 0.

Exemple:
t = (int *)calloc(100, sizeof(int)); /* t tableau de 100 entiers = à 0 */

- q = realloc(p, t); réalloue la zone pointée par p dans une zone de taille t octets
pointée par q avec recopie (tronquée si la nouvelle zone est plus petite).

.8 Les fonctions

.8.1 Définition

[<classe d'allocation>] [<type>] identificateur(<paramètres et leur type>)


<bloc>
Exemple:
float power( float x, int n) /* fonction qui retourne un reel */
{ float p=1.0; /* variable locale */
while (n--) p*=x;
return(p); /* valeur retournée */
}

x=power(3.5, 2*n); /* appel de la fonction */

Remarque: pas de contrôle sur le nombre et type des paramètres réels

Règles de passage des arguments:


 Passage des arguments s'effectue par Valeur
 Passage par référence s'effectue en passant un Pointeur
 On peut passer un tableau t: t est pointeur
 Passage d'une structure: un pointeur sur la structure

Exemple:
void swap(int *x, int *y)
{ int aux;
aux = *x ;
*x = *y ;
*y = aux ;
}

a = 1;

Professeur: ASSALE Adjé Louis 19/31 INP-HB


Langage C

b = 2;
swap (&a, &b); /* appel de la fonction */

.8.2 Fonctions récursives

Une fonction récursive est une fonction qui s'appelle elle-même dans sa
définition.

Exemple: la somme des valeurs d'un arbre étiqueté par des nombres entiers.

typedef struct nœud 2


{ int info; 5
struct nœud *gauche, *droite;
3
};
7 6

sigma(nœud *a)
{ if(a = = NULL) return (0); /* condition d'arrêt */
else return (ainfo + sigma(agauche) + sigma(adroit));
}

.8.3 Les pointeurs sur les fonctions

int f() fonction qui retourne un entier


int *f() fonction qui retourne un pointeur sur un entier
int (*pf)() pointeur sur une fonction qui retourne un entier

.8.3.1 Affectation de fonctions

int f1(x) { … };
int f2(x) { … };
int f3(x) { … };
int(*pf)();

if (x = = 1)
pf = f1; /* affectation d'une fonction à pf */
else if (x = = 2)
pf = f2;
else pf=f3;

Professeur: ASSALE Adjé Louis 20/31 INP-HB


Langage C

z = (*pf)(3); /* appel de la fonction pointée par pf */

.8.3.2 Tableau de fonctions

int (*tpf[ ])() = {f1, f2, f3};


/* tpf tableau de 3 pointeurs sur f1, f2, f3 */
z = (*tpf[0])(y); /* appel de f1 */

typedef int (*adfonc)();


adfonc pf, tpf[ ] = {f1, f2, f3};

.8.3.3 Passage de fonctions en arguments de fonctions

somme ( float a, float b, float (*f)());


{ float h, z;
int n=100, I;
h = (b-a)/n;
z = h/2*((*f)(a) + (*f)(b));
for(i = 1; i < n; i++)
z = z + h*(*f)(a + i*h);
return (z);
}

y = somme (0.1, 0.2, sin); /* appel de la fonction */

Remarque : en Turbo C, il faut préciser le nombre d’arguments et le type de


chaque argument pour les pointeurs sur fonction.

.9 Récupération des arguments d'une commande

main() peut avoir deux arguments.

Soit le fichier prog.c contenant le programme suivant:


main(int argc, char *argv[ ])
{ …}

argc : le nombre des arguments de la commande


argv : tableau de chaînes contenant les arguments

Professeur: ASSALE Adjé Louis 21/31 INP-HB


Langage C

Si on exécute la commande prog de la manière suivante:


prog f1.c –a 3

On aura : argc = 4
argv[0] = "prog"
argv[1] = "f1.c"
argv[2] = "-a"
argv[3] = "3"
argv[4] = NULL
car les arguments sont affectés au lancement du programme.

Exemple: Programme qui doit avoir au moins un argument autre que le nom du
programme et qui affiche ses arguments à l'écran.

main(int argc, char * argv[ ])


{ int i;
if (argc = =1)
printf("Le programme doit avoir au moins un argument\n");
else for(i = 1; i < argc; i++)
printf("%s\n", argv[i]);
}

.10 La compilation

.10.1 Compilation et edition de liens sous UNIX

Une commande unique cc.

cc f1.c f2.c
- compile f1 et f2
- engendre f1.o et f2.o
- engendre a.out qui est exécutable si f1 ou f2 contient main()

cc f1.c f2.c –o exec


- range l'exécutable dans exec

cc f1.o f2.o f3.c –o exec


- compile f3 et engender f3.o
- édite les liens entre f1, f2 et f3
- range l'exécutable dans exec

Professeur: ASSALE Adjé Louis 22/31 INP-HB


Langage C

.10.2 Le pré-compilateur C

Traite les lignes commençant par #.

.10.2.1 Inclusion de fichiers

#include "f1"
#include "../d/h"
#include<stdio.h>
 #include "/usr/include/stdio.h"

.10.2.2 Macro – definition

#define TMAX 255 /* remplace dans le fichier toute occurrence de la


chaîne TMAX par 255 */

#define BEGIN {
#define END }
#define IF if(
#define THEN )

IF x = = 0 THEN if (x = = 0)
BEGIN {
x++;  x++;
END }

- Macros avec des arguments

#define SWAP(x, y) { int aux; \


 aux = x; \
pas d'espace x = y; \
y = aux; }
\ permet des définitions sur plusieurs lignes

exemple:
for (i = 0; i < n; i++) SWAP(t[i], t[i+1]);
devient
for (i = 0; i < n; i++) { int aux;
aux = t[i];

Professeur: ASSALE Adjé Louis 23/31 INP-HB


Langage C

t[i] = t[i+1];
t[i+1] = aux;}

- Attention au parenthèse

#define CARRE(x) (x)*(x)


CARRE(a+b)  (a+b)*(a+b)

#define SQR(x) x*x


SQR(a+b)  a+b*a+b

Le paramètre x est substitué TEXTUELLEMENT

- Noms de macro et minuscules

#define k 100
ak=3;  a100 = 3;
tous les k sont substitués

- Macro génération est récursive

#define PERM(t, inf, sup) { int i; \


for (i = inf; i < sup; i++) \
SWAP(t[i], t[i+1];}
- Macro définition à la compilation

cc -DTMAX=100 f1.c f2.c


compile f1 et f2 comme s'ils contenaient une ligne #define TMAX 100

.10.2.3 Compilation conditionnelle

#undef DEBUG /* supprime la définition de DEBUG qui peut ainsi


être modifié */

#ifdef XYZ /* le texte est compilé s'il existe une définition


… sur XYZ */
#endif

#ifndef VRAI /* compilation si VRAI n'est pas définie */



#endif

Professeur: ASSALE Adjé Louis 24/31 INP-HB


Langage C

#if expression /* compilation si l'expression à un valeur


… différente de 0 */
#endif

#if expression #ifdef nom_macro


… …
#else ou #else /* compilation alternative */
… …
#endif #endif

Exemples:
#ifdef DEBUG
printf("Appel de f()");
#endif
cc –DDEBUG …

#ifdef NUMELEC
#include "numelec.h"
#else /* version */
#include "standard.h"
#endif

/* pour éviter de redéfinir des macros pouvant être définies dans des fichiers
importés par #include */

#ifndef VRAI
#define VRAI 1
#define FAUX 0
#endif

Professeur: ASSALE Adjé Louis 25/31 INP-HB


Langage C

.11 Manipulation de Fichiers

Les fonctions d’entrées/sorties printf, scanf,…, lisent toutes l’entrée standard


(stdin : le clavier) ou écrivent sur la sortie standard (stdout : l’écran). Cette
entrée et cette sortie sont prédéfinies par le système d’exploitation.

Pour accéder à un fichier non relié au programme la bibliothèque fournit toute


une liste de fonctions et macroinstructions permettant d’ouvrir un fichier (le
rendre accessible), d’initialiser ou déplacer un pointeur sur ce fichier et de
préciser le mode d’utilisation (lecture, écriture, ajout…)

Le problème est de relier le nom externe du fichier à des instructions qui


manipulent réellement les données.

.11.1 Ouverture/Fermeture d’un fichier

On verra principalement les accès fichiers effectués au travers d’une mémoire


tampon (buffer). Dans ce mode il est nécessaire d’ouvrir un « flux » (stream)
entre le buffer et le périphérique auquel on souhaite accéder qui peut être un
fichier disque, un port,…

L’ouverture d’un flux s’obtient à l’aide de la fonction fopen qui, entre autres
opérations, réserve un tampon mémoire et retourne un pointeur permettant
l’accès à ce tampon.
Syntaxe : pf = fopen(nom, mode) ;

nom est une chaîne de caractères désignant le nom externe du fichier : pour un
fichier disque c’est le nom du fichier sous DOS.
Exemple : a :monfich.txt 

mode est aussi une chaîne de caractères, elle permet de préciser le mode
d’accès : lecture (r), écriture (w), ou ajout (a). Plusieurs options sont
possibles, pour plus de détails se reporter à la fin de ce chapitre.

pf est un pointeur sur une structure, notée FILE, prédéfinie dans stdio.h. Toutes
les manipulations ultérieures sur le fichier utiliseront ce pointeur.

Exemple :

File *p ; / déclaration du pointeur p */


p = fopen(a :monfich.txt,r) ; /* ouverture du fichier en
mode lecture seule) */

Professeur: ASSALE Adjé Louis 26/31 INP-HB


Langage C

if(p = = 0) puts(accès impossible) ; /* test de réussite de l’opération */




fclose(p) ; /* fermeture du fichier */

la fonction fclose ferme le flux ouvert par fopen, vide le buffer et libère la
mémoire et le pointeur p associé au flux. Oublier de fermer un flux peut être très
dangereux !

Plusieurs flux sont ouverts par le système lui même, si bien que l’utilisateur peut
accéder directement aux périphériques correspondants, il s’agit de :

nom E/S mode fichier

stdin E texte entrée standard (clavier)


stdout S texte sortie standard (écran)
stderr S texte erreur standard (disque)
stdaux E/S binaire E/S auxilliare (port série)
stdprn E/S binaire E/S parallèle (imprimante)

exemple :

fputc(ch, stdprn) ; /* envoie le caractère ch sur l’imprimante */

Dans stdio.h les fonctions fopen rt fclose sont déclarées par les prototypes :

FILE *fopen(const char *filename, char *mode) ;


int fclose(FILE *stream) ;

.11.2 Lecture/Ecriture octet par octet

Les fonctions de lecture/écriture les plus simples travaillent octet par octet : ce
sont fgetc et fputc. Il existe également deux macroinstructions qui remplissent le
même rôle : getc et putc.

fgetc lit un octet dans le flux et renvoie l’octet pointé en cas de succès, EOF en
cas d’erreur. Le pointeur est automatiquement incrémenté.

Exemple :

char mot ;
FILE *pf ; / déclaration d’un pointeur sur un fichier */

Professeur: ASSALE Adjé Louis 27/31 INP-HB


Langage C

pf = fopen(fich.dat,r) ; /* ouverture du flux */


mot = fgtc(pf) ; /* lecture du premier octet */

fputc écrit un octet, passé à la fonction comme premier paramètre, dans le flux.

Exemple :

/* avec les mêmes déclarations que dans l’exemple précédent */

pf = fopen(fich.dat, r+) ; /* ouverture en mode mise à jour */



fputc(mot, pf) /* écriture dans le flux */

Comme fgetc, fputc retourne EOF en cas d’erreur, et sinon la valeur de l’octet
passé comme paramètre. putc est une macroinstruction qui réalise la même
opération.

Dans stdio.h ces fonctions sont déclarées par les prototypes :

int fgetc(FILE *stream) ;


int fputc(char c, FILE *stream);

.11.3 Déplacement du pointeur

Le pointeur obtenu par appel de fopen ne représente pas une adresse mémoire et
ne peut être manipulé directement: ++pf ou (pf+1) n’ont pas de sens. Il faut
appeler des fonctions spécifiques pour se déplacer dans le fichier (fseek, rewind)
ou obtenir des informations sur la position courante du pointeur (ftell, feof).

- fseek permet de déplacer le pointeur de flux. Les paramètres passés sont le


pointeur de flux, la valeur du déplacement souhaité et l’origine du déplacement.

Exemple
fseek (pf, 3802L,0); /* le pointeur pf est amené à pointer sur le 3802 éme
octet, partant du début de fichier */

Le deuxième paramètre est un entier de type long et le troisième peut prendre les
valeurs 0, 1 ou 2 pour exprimer un déplacement depuis le début du fichier, la
position courante ou la fin respectivement.

- rewind est équivalent à fseek(pf, 0L,0): cette fonction ramène le pointeur en


début de fichier.

Professeur: ASSALE Adjé Louis 28/31 INP-HB


Langage C

- ftell donne en nombre d’octets la position courante du pointeur, la valeur


retournée est du type long int.

- feof indique que le pointeur est en fin de fichier: cette fonction retourne la
valeur 0 dans ce cas.

Dans stdio.h ces fonctions sont déclarées par les prototypes:

int fseek(FILE *stream, long offset, int whence);


void rewind(FILE *stream);
long ftell(FILE *stream);
int feof(FILE *stream);

.11.4 Lecture/Ecriture d’objets quelconques

Les fonctions fread et fwrite permettent de lire ou d’écrire des objets de taille
quelconque, taille exprimée en nombre d’octets.

Exemples d’utilisation :
fread(pt_obj, sizeof(int),n,pt_fich) ;
fwrite(pt_obj, sizeof(int),n,pt_fich);

Le premier parameter passé est un pointeur sur la liste d’objets. Il représente,


dans le cas d’un fread l’adresse à partir de laquelle devront être rangés les objets
lus, dans le cas d’un fwrite l’adresse à partir de laquelle on va chercher les objets
à écrire.
Le deuxième paramètre représente la taille, en nombree d’octets, des objets à lire
ou à écrire. Dans cet exemple sizeof(int) renvoie la valeur en octet d’un entier.
Le troisième paramètre est le nombre d’objets à lire ou à écrire qui ne doit pas
être confondu avec le nombre d’octets.
Enfin le dernier paramètre est un pointeur sur le fichier, généralement initialisé
par appel de fopen.

Ces desux fonctions renvoient le nombre d’objets effectivement lus ou écrits,


nombre qui peut être inférieur à n si un incident est survenu en cours
d’opération.

.11.5 Lectures/Ecritures formatées

Ils s’agit d’extensions des fonctions scanf et printf :

Professeur: ASSALE Adjé Louis 29/31 INP-HB


Langage C

Les octets lus ou écrits dans le fichier le sont en nombre compatible avec le type
(4 pour un float par exemple), et interprétés conformément à ce type.

Exemple :

fprintf(stdprn, essai d’écriture sur l’imprimante %d\n, nb) ;

Le premier paramètre passé à la fonction est un pointeur sur le fichier (ici stdprn
pour le port parallèle), les suivants sont identiques aux paramètres de printf ou
de scanf.

La fonction fscanf retourne le nombre de champs d’entrée correctement lus,


convertis et mémorisés. Si aucun champ n’est mémorisé, la valeur retournée est
0.
La fonction fprintf retourne le nombre d’octets écrits. En cas d’erreur elle
retourne EOF.

.11.6 Lectures/Ecritures de chaînes de caractères

- fgets et fputs permettent de lire ou d’écrire des chaînes de caractères dans un


fichier.

Exemple :
fgets(str, n, pt_fich) ;

La fonction fgets lit des caractères depuis le flux d’entrée pt_fich et les place
dans la chaîne str. La fonction cesse la lecture soit lorsque n-1 caractères ont été
lus, soit à la lecture d’un caractère d’interligne (‘\n’). fgets ne recopie pas le
caractère d’interligne dans str. Le dernier caractère lu est toujours suivi d’un
caractère nul (‘\0’) dans str.

La fonction fputs recopie dans le flux de sortie pt_fich la chaîne pointée par str
et terminée par un caractère nul, elle n’ajoute pas de caractère d’interligne.

fputs(str,pt_fich) ;

.11.7 Compléments sur le paramètre mode passé à fopen

Mode r  : lecture seule


Le pointeur est placé en début de fichier par fopen, il sera incrémenté
automatiquement à chaque lecture.

Professeur: ASSALE Adjé Louis 30/31 INP-HB


Langage C

Mode w : écriture seule


Ce mode crée un fichier et place le pointeur au début. Si un fichier de même
nom existait déjà il sera écrasé.

Mode a : ajout en fin de fichier (écriture)


N’écrase pas le fichier existant : les opérations d’écriture se font à la fin.

Options t,b (exemples : rb, wt)


En mode binaire (b) les données sont interprétées comme des valeurs
numériques et ne sont pas modifiées.
En mode texte (t) les caractères (CR, LF) sont interprétés comme tels.

Option mise à jour + (ex : r+b)


Cette option autorise la lecture et l’écriture mais deux opérations successives de
type différent (ex : 1 lecture puis 1 écriture) doivent être séparées par un appel à
fseek.

r+ : le fichier doit déjà exister, il n’est pas modifié par fopen.
w+ : le fichier est crée ou écrasé par fopen, ce mode n’est intéressant que pour
un nouveau fichier.

Professeur: ASSALE Adjé Louis 31/31 INP-HB

Vous aimerez peut-être aussi