Documente Academic
Documente Profesional
Documente Cultură
Rcursivit
David Pointcheval
Plan
1 - Fonctions 2 - Rcursivit
Programmation C - ENSTA - 2
Prototype de fonction
Le prototype dune fonction (ou en-tte) prcise la vue de lextrieur de la fonction :
le nom de la fonction les types des arguments pris en entre le type de retour
int addition(int a, int b) double puissance(double a, int e)
Prototypes (suite)
Exemple de prototype de fonction : double puissance(double a, int e)
Nom de la fonction Type du rsultat Premier argument type nom local
David Pointcheval LIENS - CNRS
Deuxime argument
Programmation C - ENSTA - 4
Programmation C - ENSTA - 3
Utilisation
Pour le prototype suivant on utilisera la fonction puissance : o x est un double, et n un int tous deux dclars et initialiss, le rsultat ira dans la variable y, de type double, dclare : affectation (ou initialisation)
David Pointcheval LIENS - CNRS Programmation C - ENSTA - 5
Utilisation (suite)
Le prototype suffit au compilateur dans un premier temps Le mode opratoire nest utile que dans un deuxime temps : dition des liens une fonction peut sappeler elle-mme, car son en-tte est dj connue
David Pointcheval LIENS - CNRS Programmation C - ENSTA - 6
Rcursivit
La puissance peut tre exprime rcursivement :
ae = a * ae-1 a0 = 1 Critre darrt
y = puissance(x,n)
Exemple I
La fonction puissance peut tre programme de la faon suivante :
double puissance(double a, int e) { if (e == 0) return 1; Critre return puissance(a,e-1)*a; }
Exemple I - analyse
lappel de la fonction puissance le double 2.0 double y; est stock dans a y = puissance(2.0, et lint 2 est stock dans e
darrt
2);
Si e=0 le rsultat est 1 return 1; sinon, le rsultat est ae-1 * a return puissance(a,e-1)*a;
David Pointcheval LIENS - CNRS Programmation C - ENSTA - 9 David Pointcheval LIENS - CNRS
Exemple I - excution
puissance(2.0,2) a 2.0 e 2 puissance(2.0,1)*2.0 puissance(2.0,1) double y; a 2.0 e 1 y = puissance(2.0, 2); puissance(2.0,0)*2.0 double puissance(double a, int e) puissance(2.0,0) { a 2.0 if (e == 0) return 1; e 0 return puissance(a,e-1)*a; } 1 1 * 2.0 = 2.0 2.0 * 2.0 = 4.0
David Pointcheval LIENS - CNRS Programmation C - ENSTA - 11
Variables locales
chaque excution de la fonction puissance possde ses propres variables locales a et e, dtruites la fin de la fonction
Programmation C - ENSTA - 12
Exemple II
Une programmation quivalente serait :
double puissance(double a, int e) { double z; if (e == 0) return 1; Critre z = puissance(a,e-1); return z*a; } 4.0
Exemple II - excution
puissance(2.0,2)
puissance(2.0,2) a 2.0 e 2 z 2.0
darrt
puissance(2.0,0) a 2.0 e 0 z
Programmation C - ENSTA - 14
Exemple II - pile
4.0 puissance(2.0,2) a 2.0 e 2 z 2.0
puissance(2.0,0) a 2.0 e 0 z
Programmation C - ENSTA - 15
Lappel rcursif nest pas la dernire instruction de la fonction lopration est effectue au dpilement , en remontant
David Pointcheval LIENS - CNRS Programmation C - ENSTA - 16
Exemple III
Laddition entire peut tre reprogramme avec seulement des incrmentations et dcrmentations :
a + b = (a+1) + (b-1) a + 0 = a Critre darrt
int addition(int a, int b) { if (b == 0) return a; return addition(a+1,b-1); }
David Pointcheval LIENS - CNRS Programmation C - ENSTA - 17
4 1 5 addition(5,0) a b 5 0
Programmation C - ENSTA - 18
Rcursivit terminale
int addition(int a, int b) { if (b == 0) return a; return addition(a+1,b-1); }
4 1 5 addition(5,0) a b 5 0
Lappel rcursif est la dernire instruction de la fonction une fois le rsultat obtenu (lorsque b=0) le rsultat est propag au dpilement
David Pointcheval LIENS - CNRS Programmation C - ENSTA - 20
Programmation C - ENSTA - 19
Rcursivit multiple
Pour svaluer, une fonction peut faire plusieurs fois appel elle-mme Ex : Fibonacci
F(n) = F(n-2) + F(n-1) F(0) = 1 Critres darrt F(1) = 1
Exemple IV
La suite de Fibonacci peut donc tre programme de la faon suivante :
int fibonacci(int n) { if (n < 2) return 1; Critre darrt return fibonacci(n-2) + fibonacci(n-1); }
Programmation C - ENSTA - 21
Programmation C - ENSTA - 22
Exemple IV - excution
5 fibonacci(4) 2 fibonacci(2) 1 1 fibonacci(1) fibonacci(1) fibonacci(0) fibonacci(0)
int fibonacci(int n) { if (n < 2) return 1; return fibonacci(n-2) + fibonacci(n-1); }
David Pointcheval LIENS - CNRS
Rcursivit : avantages
La programmation rcursive est trs proche de la dfinition mathmatique du problme trs facile implmenter Mais, ne pas oublier les critres darrt, au risque dune boucle sans fin !
David Pointcheval LIENS - CNRS
3 fibonacci(3) 1 2 fibonacci(2) 1 1
fibonacci(1)
pas efficace !
Programmation C - ENSTA - 23 Programmation C - ENSTA - 24
Rcursivit (suite)
Contrairement certaines ides reues, une fonction programme rcursivement est aussi efficace que sa version itrative (lorsque les calculs sont les mmes, contrairement Fibonacci) Voir les exemples en TP
David Pointcheval LIENS - CNRS
Conclusion
Ne pas hsiter programmer de faon rcursive crire la relation mathmatique dinduction ne pas oublier le ou les cas triviaux (conditions darrt)
David Pointcheval LIENS - CNRS
Programmation C - ENSTA - 25
Programmation C - ENSTA - 26