Calculabilité, correction, terminaison et compléxité 1/23
Sommaire 1. 2. 3. 4. 5. Calculabilité Terminaison et correction d'algorithmes Complexité Exemple : tri Pour aller plus loin 2/23
Calculabilité fonction calculable : une fonction f est calculable s'il existe une méthode précise qui, étant donné un argument x, permet d'obtenir l'image f (x) en un nombre fini d'étapes. Plusieurs formalisations mathématiques de ce que peut être une méthode de calcul existent et sont équivalentes : fonctions récursives machine de Turing lambda-calcul machine à compteurs automate cellulaire Elles définissent exactement les mêmes fonctions calculables. 3/23
Qu'est ce qui est programmable? Considérons les fonctions du type : f : N N La plupart des fonctions que nous connaissons sont programmables : f (x) = x 2 f (x) = x 2 + 1 f (x) = cos(x) premier(x) = { 1 0 si x est premier sinon 4/23
Nombre de programmes??? Un exemple : la fonction constante égale à 0. function f(n){return n n + x x; } Si on remplace x par n'importe quel entier on peut en écrire une infinité. On peut donc les numéroter (en partant du plus court et dans l'ordre lexicographique) Il y a donc autant de programmes qu'il y a de nombres entiers. En désignant par l'ensembles des programmes de N N on obtient : card( ) = card(n) = ℵ 0 ℵ 0 représente l'infini dénombrable 5/23
Nombre de fonctions calculables Il ne peut pas y avoir plus de fonctions calculables qu'il n'y a de programmes. On en déduit : card( c ) = card(n) = ℵ 0 6/23
Nombre de fonctions de N N Une infinité : mais est-ce la même infinité que les fonctions calculables? A chaque partie A de N, on peut associer sas fonction indicatrice : f A : N n N { O 1 si si n A n A On définit ainsi une fonction ϕ de l'ensemble (N) des parties de N dans l'ensemble 0,1 ϕ : (N) A 0,1 f A ϕ est une fonction bijective, on en déduit : card( (N)) = card( 0,1 ) Un théorème de Cantor établit que pour un ensemble E : card( (E)) > card(e) 7/23
Nombre de fonctions de N N On en déduit que : comme on en déduit que : 0,1 card( 0,1 Conclusion : les fonctions non calculables sont infiniment plus nombreuses que les fonctions calculables Questions : pouvez vous en citer une??? ) > (N) card( ) > card(n) 8/23
Problème de l'arrêt ou terminaison des programmes Un problème typique : Y a t'il un bug ou est ce le déroulement normal de l'algorithme Un exemple : le calcul de la factorielle d'un nombre function factorielle(n) { // spécifications : n > 0 res=1; while (n > 1) { res*=n; n--; } return res; } La terminaison de ce programme n'est pas difficile à montrer 9/23
Problème de l'arrêt ou terminaison des programmes Un autre exemple : function collatz(n) { // spécification : n > 0 if (n==1) return 1; if (n%2==0) n/=2; else n=3*n+1; } Là c'est moins évident et pour cause 10/23
Un résultat paradoxal Supposons que l'on puisse écrire un programme prennant en paramètre une fonction et qui retourne vrai si cette fonction s'arrête quelque soit la (ou les) donnée(s) d'entrée(s). Si un tel programme existe et qu'il est correct alors on peut l'utiliser sur la fonction collatz et à nous la fortune. Que dire de cette fonction : function une_fonction() { if (arret_garanti(une_fonction())) une_fonction(); } Le calcul de une_fonction() s'arrête si et seulement si il ne s'arrête pas 11/23
Comment savoir qu'un algorithme est correct? Problèmes rencontrés en algorithmique : Algorithme itératif contenant une boucle infinie : problème de terminaison Algorithme récursif ne contenant pas la base : problème de terminaison. Algorithme se terminant mais ne donnant pas toujours la solution correcte : problème de correction (validité). Algorithme faisant des erreurs numériques : problème issu de l arithmétique de la machine. 12/23
Comment savoir qu'un algorithme est correct? Méthodes logiques pour la vérification des algorithmes : Tests : on essaie l algorithme sur plusieurs données pour observer et corriger les anomalies de l algorithme Preuves : on prouve mathématiquement que l algorithme est valide Inconvénients : Les tests ne permettent pas toujours de trouver les bugs obscurs. L utilisation unique des tests est parfois très dangereuse. Les preuves mathématiques peuvent parfois être fausses, et donc produisent des algorithmes faux ou contenant des erreurs. La solution : utiliser parallèlement des preuves mathématiques et des tests 13/23
Terminaison et correction d'un algorithme Définition : un algorithme se termine, si son exécution sur machine s arrête toujours quelque soit la nature des données en entrée Définition: un algorithme est correct (ou valide), s il se termine, et si le résultat qu il fournit est toujours correct, c est-à-dire l algorithme fait bien ce qu il est supposé faire dans sa spécification. 14/23
Preuve d un algorithme récursif Preuve de terminaison : montrer que l algorithme parvient toujours au traitement de la base en un nombre fini d appels. Méthode : La preuve s effectue par induction (récurrence) sur la taille du problème à résoudre La base de la récurrence est celle de la récursivité L étape de la récurrence : on suppose que l algorithme se termine pour les appels récursifs précédents, et on montre qu il se termine pour l'appel courant Preuve de correction : montrer que l algorithme calcul bien le résultat après la terminaison de tous les appels récursifs Méthode : idem terminaison 15/23
Preuve d un algorithme itératif Méthode : Analyser les boucles de l'algorithme, une par une en commençant par la boucle la plus interne en cas de boucles imbriquées Concevoir pour chaque boucle, un invariant de boucle Prouver que les invariants de boucle sont valides (par récurrence) Utiliser les invariants de boucle pour prouver que l'algorithme se termine Utiliser les invariants de boucle pour prouver que l'algorithme calcule le résultat correct Définition : un invariant de boucle est une propriété qui lie les variables d une boucle et qui est toujours vraie après chaque passage dans la boucle 16/23
Compléxité des algorithmes Comment évaluer les performances d'un algorithme? Différents algorithmes ont des coûts différents en terme de temps d'exécution(nombre d'opérations)et de taille mémoire. Ces deux concepts sont appelés complexité en temps et en espace de l'algorithme La complexité algorithmique permet de mesurer les performances d'un algorithme et de le comparer avec d'autres algortihmes réalisant les mêmes fonctionnalités. La complexité algorithmique est un concept fondamental pour tout informaticien, elle permet de déterminer si un algorithme a et meilleur qu'un algortihme b et s'il est optimal ou s'il ne doit pas être utilisé... 17/23
Temps d'exécution Le temps d'exécution d'un programme dépend : 1. 2. 3. 4. du nombre de données, de la taille du code, du type d'ordinateur utilisé (processeur,mémoire), de la complexité en temps de l'algorithme «abstrait» sous-jacent. Soit n la taille des données du problème et T(n) le temps d'exécution de l'algorithme. On distingue : Le temps du plus mauvais cas T max (n) qui correspond au temps maximum pris par l'algorithme pour un problème de taille n. le temps moyen T moy (n) d'exécution sur des données de taille n ( suppositions sur la distribution des données). 18/23
Temps d'exécution Règles générales : 1. le temps d'exécution ( constant c, ) d'une affectation ou d'un test est considéré comme 2. le temps d'une séquence d'instructions est la somme des la composent, des instructions qui 3. le temps d'un branchement conditionnel est égal au t. e. du test plus le max des deux t. e. correspondant aux deux alternatives 4. t. e. le temps d'une boucle est égal à la somme du coût du test + du corps de la boucle multiplié par le nombre d'itérations. t. e. 19/23
Quelques exemples de complexité Notation de Landau : f (n) O(g(n)), f est bornée, par le dessus, par g asymptotiquement (à un facteur près). Lorsque n on a f (n) g(n). k pour k > 0. Exemples : O(1) O(log(n)) : bornée par une constante O((log(n))c) O(n) : logarithmique : linéaire O(n. log(n)) O( n 2 ) O( n c ) O( c n ) O(n!) : polylogarithmique : parfois appelée «linéarithmique», ou «quasi-linéaire» : quadratique : polynomiale : exponentielle, parfois «géométrique» : factorielle 20/23
Exemple : algorithmes de tris O( n 2 ) : tri à bulles, tri par sélection, tri par insertion tri fusion : O(n. log(n)) (structures de données supplémentaires) tri rapide (quicksort) : O(n. log(n)) en moyenne mais O( n 2 ) dans le pire des cas tri par tas (heapsort) : O(n. log(n)) 21/23
22/23
Questions??? 23/23