SlideShare ist ein Scribd-Unternehmen logo
1 von 104
Downloaden Sie, um offline zu lesen
Algorithmique et
   complexité
       Mr. Slim Mesfar

  Mail: mesfarslim@yahoo.fr




       A.U. 2011-2012
Plan du cours
   Chap-1: Introduction & motivations
   Chap-2: ComplexitĂ© & optimalitĂ©
   Chap-3: Algorithmes de tri:
    analyse et estimation de la complexité
   Chap-4: RĂ©cursivitĂ©
    ïź   DiffĂ©rents types de rĂ©cursivitĂ©
    ïź   DĂ©rĂ©cursivation d’algorithmes
    ïź   RĂ©cursivitĂ© terminale et non terminale
    ïź   Paradigme « diviser pour rĂ©gner »
   Chap-5: Graphes et arbres
   Chap-6: Arbres binaires de recherche
Objectifs du cours
   Elaborer des algorithmes performants et efficaces
   Comprendre la notion de complexitĂ© d’un algorithme
   MaĂźtriser la rĂ©cursivitĂ© (simple, multiple, mutuelle,
    imbriquée)
   Savoir dĂ©rĂ©cursiver des algorithmes simples et multiples
   MaĂźtriser la dĂ©marche « diviser pour rĂ©gner »
   Savoir estimer la complexitĂ© d’un algorithme itĂ©ratif ou
    récursif pouvant conduire à des récurrences linéaires
    d’ordre 1, d’ordre 2 et des rĂ©currences de type « diviser
    régner »
   ConnaĂźtre les diffĂ©rents algorithmes de tri et estimer leur
    complexité
   Elaborer des algorithmes Ă  base de graphes et d’arbres
   RĂ©aliser des algorithmes de parcours de graphes et d’arbres
Chapitre 1 – Introduction
     et motivations
Introduction
Un algorithme = une suite ordonnĂ©e d'opĂ©rations
 ou d'instruction écrites pour la résolution d'un
 problÚme donné.
 Algorithme = une suite d’actions que devra
 effectuer un automate pour arriver à partir d’un
 état initial, en un temps fini, à un résultat

   L’algorithmique dĂ©signe le processus de
    recherche d’algorithme
Structures de données
   Une structure de donnĂ©es indique la maniĂšre
    d'organisation des données dans la mémoire.
   Le choix d'une structure de donnĂ©es adĂ©quate
    dépend généralement du problÚme à résoudre.
   Deux types de structures de donnĂ©es :
    ïź   Statiques : Les donnĂ©es peuvent ĂȘtre manipulĂ©es dans
        la mémoire dans un espace statique alloué dÚs le début
        de résolution du problÚme. Ex : les tableaux
    ïź   Dynamiques : On peut allouer de la mĂ©moire pour y
        stocker des données au fur et à mesure des besoins de
        la résolution du problÚme. Ex: liste chainée, pile, file, 

         notion des pointeurs  nĂ©cessitĂ© de la gestion des
        liens entre les données d'un problÚme en mémoire.
QualitĂ©s d’un bon algorithme
   Correct: Il faut que le programme exĂ©cute
    correctement les tùches pour lesquelles il a été
    conçu
   Complet: Il faut que le programme considĂšre
    tous les cas possibles et donne un résultat dans
    chaque cas.
   Efficace: Il faut que le programme exĂ©cute sa
    tĂąche avec efficacitĂ© c’est Ă  dire avec un coĂ»t
    minimal. Le coût pour un ordinateur se mesure
    en termes de temps de calcul et d’espace
    mémoire nécessaire.
Exemple : Calcul de la valeur d’un polynîme
   Soit P(X) un polynĂŽme de degrĂ© n
    P(X) = anXn + an-1Xn-1 + ... + a1X + a0
   OĂč,
    ïź   n : entier naturel
    ïź   an, an-1, ..., a1, a0 : les coefficients du polynĂŽme
   1Ăšre variante :
dĂ©but                                        CoĂ»t de l’algorithme :
    P=0                                      - (n+1) additions
    Pour i de 0 Ă  n faire                    - (n+1) multiplications
                                             - (n+1) puissances
         P = P+ ai*Xi
    finpour
fin
Exemple : Calcul de la valeur d’un polynîme
   2Ăšme variante :
                              CoĂ»t de l’algorithme :
debut                         - (n+1) additions
      Inter=1                 - 2(n+1) multiplications
      P =0
      Pour i de 0 Ă  N faire
         P = P+ Inter *ai
         Inter = Inter * X
      finpour
Fin
Exemple : Calcul de la valeur d’un polynîme
   3Ăšme variante : SchĂ©ma de Horner

P(x) = (
.(((anx+an-1)x+an-2)x+an-3)
..)x+a0

début
   P = an
   Pour i de n-1 à 0 (pas = –1) faire
        P = P*X + ai
                                        CoĂ»t de l’algorithme :
   finpour
                                        - n additions
Fin                                     - n multiplications

 NĂ©cessitĂ© d’estimer le coĂ»t d’un algorithme avant de l’écrire
  et l’implĂ©menter
Chapitre 2 – ComplexitĂ©
     et optimalité
DĂ©finitions
   la complexitĂ© d'un algorithme est la mesure du
    nombre d'opérations fondamentales qu'il effectue
    sur un jeu de données.
   La complexitĂ© est exprimĂ©e comme une fonction
    de la taille du jeu de données.
   La complexitĂ© d'un algorithme est souvent
    déterminée à travers une description
    mathématique du comportement de cet
    algorithme.
DĂ©finitions
   On note Dn l’ensemble des donnĂ©es de taille n et T(d) le
    coĂ»t de l’algorithme sur la donnĂ©e d.
   On dĂ©finit 3 types de complexitĂ© :
    ïź   ComplexitĂ© au meilleur :
        C'est le plus petit nombre d'opérations qu'aura à exécuter l'algorithme
        sur un jeu de données de taille fixée, ici à n.
    ïź   ComplexitĂ© au pire :
        C'est le plus grand nombre d'opérations qu'aura à exécuter
        l'algorithme sur un jeu de données de taille fixée, ici à n.
    ïź   ComplexitĂ© en moyenne :

        C'est la moyenne des complexités de l'algorithme sur des jeux de
        données de taille n.
DĂ©finitions
   C'est l'analyse pessimiste ou au pire qui est gĂ©nĂ©ralement
    adoptée.
   En effet, de nombreux algorithmes fonctionnent la plupart
    du temps dans la situation la plus mauvaise pour eux.
     l'analyse au pire des cas donne une limite supĂ©rieure de
    la performance et elle garantit qu'un algorithme ne fera
    jamais moins bien que ce qu'on a Ă©tabli.
     Un algorithme est dit optimal si sa complexitĂ© est la
    complexité minimale parmi les algorithmes de sa classe.
   MĂȘme si on s’intĂ©resse quasi-exclusivement Ă  la complexitĂ©
    en temps des algorithmes. Il est parfois intéressant de
    s’intĂ©resser Ă  d’autres ressources, comme la complexitĂ© en
    espace (taille de l’espace mĂ©moire utilisĂ©), la largeur de
    bande passante requise, etc.
Notations mathématiques
   La notation O est celle qui est le plus communĂ©ment
    utilisée pour expliquer formellement les performances d'un
    algorithme.
   Cette notation exprime la limite supĂ©rieure d'une fonction
    dans un facteur constant.

     La notation O reflĂšte la courbe ou l'ordre croissance d'un
    algorithme.
   Les rĂšgles de la notation O sont les suivantes :
    ïź   Les termes constants : O(c) = O(1)
    ïź   Les constantes multiplicatives sont omises : O(cT ) = cO(T) = O(T)
    ïź   L'addition est rĂ©alisĂ©e en prenant le maximum : O(T1) + O(T2) =
        O(T1 + T2) = max(O(T1);O(T2))
    ïź   La multiplication reste inchangĂ©e mais est parfois rĂ©Ă©crite d'une façon
        plus compacte :O(T1)O(T2) = O(T1T2)
Exemple
   On suppose qu’on dispose d'un algorithme dont le temps
    d'exécution est décrit par la fonction T(n) = 3n2+10n+10.
    L'utilisation des rĂšgles de la notation O nous permet de
    simplifier en :
    O(T(n)) = O(3n2 + 10n + 10) = O(3n2) = O(n2)
   Pour n = 10 nous avons :
    ïź   Temps d'exĂ©cution de 3n2 : 3(10)2 / 3(10)2+10(10)+10 = 73,2%
    ïź   Temps d'exĂ©cution de 10n : 10(10) / 3(10)2+10(10)+10 = 24,4%
    ïź   Temps d'exĂ©cution de 10 : 10 / 3(10)2+10(10)+10 = 2,4%
   Le poids de 3n2 devient encore plus grand quand n = 100,
    soit 96,7%  on peut nĂ©gliger les quantitĂ©s 10n et 10.
    Ceci explique les rĂšgles de la notation O.
Classes de complexité
   Les algorithmes usuels peuvent ĂȘtre classĂ©s en un certain
    nombre de grandes classes de complexité.
   Les complexitĂ©s les plus utilisĂ©es sont :
    ïź   Constante : O(1) AccĂ©der au premier Ă©lĂ©ment d'un ensemble de
        données
    ïź   Logarithmique : O(logn) Couper un ensemble de donnĂ©es en deux
        parties égales, puis couper ces moitiés en deux parties égales, etc.
    ïź   LinĂ©aire : O(n) Parcourir un ensemble de donnĂ©es
    ïź   Quasi-linĂ©aire : O(nlogn) Couper rĂ©pĂ©titivement un ensemble de
        données en deux et combiner les solutions partielles pour calculer la
        solution générale
    ïź   Quadratique : O(n2) Parcourir un ensemble de donnĂ©es en utilisant
        deux boucles imbriquées
    ïź   Polynomiale : O(nP) Parcourir un ensemble de donnĂ©es en utilisant
        P boucles imbriquées
    ïź   Exponentielle : O(2n) GĂ©nĂ©rer tous les sous-ensembles possibles
        d'un ensemble de données
Classes de complexité
Calcul de la complexité
   1. Cas d'une instruction simple : Ă©criture, lecture,
    affectation
    Dans le cas d'uns suite d'instructions simples, on considĂšre la
    complexité maximale.




    La complexité de cette séquence vaut max(O(1),O(1))=O(1).
Calcul de la complexité
   2. Cas d'un traitement conditionnel




   3. Cas d'un traitement itĂ©ratif : Boucle Tant Que
Calcul de la complexité
   4. Cas d'un traitement itĂ©ratif : Boucle Pour

Pour i de indDeb Ă  indFin faire
     Traitement
Fin Pour
        indFin

         ∑ O(T
       i =indDeb
                   Traitement   )
Exemples de calcul de la complexité
   Exemple 1 : Tri par insertion
    ïź   Principe : Cette mĂ©thode de tri s'apparente Ă 
        celle utilisée pour trier ses cartes dans un jeu :
        on prend une carte, tab[1], puis la deuxiĂšme,
        tab[2], que l'on place en fonction de la
        premiĂšre, ensuite la troisiĂšme tab[3] que l'on
        insĂšre Ă  sa place en fonction des deux
        premiÚres et ainsi de suite. Le principe général
        est donc de considérer que les (i-1) premiÚres
        cartes, tab[1],..., tab[i-1] sont triées et de
        placer la ie carte, tab[i], Ă  sa place parmi les
        (i-1) déjà triées, et ce jusqu'à ce que i = N.
Exemples de calcul de la complexité
   Exemple 1 : Tri par insertion
    Procédure tri_Insertion (var tab : tableau entier [N])
          i, k :entier ;
          tmp : entier ;
          Pour i de 2 Ă  N faire
             tmp ← tab[i];
             k ← i;
             Tant que k > 1 ET tab[k - 1] > tmp faire
                    tab[k] ← tab[k - 1];
                    k ← k - 1;
             Fin Tant que
             tab[k] ← tmp;
          Fin pour
    Fin
Exemples de calcul de la complexité
Exemple 1 : Tri par insertion
 Calcul de la complexitĂ©:
  ïź   la taille du tableau Ă  trier est n.
  ïź   On a deux boucles imbriquĂ©es :
          La premiĂšre indique l'Ă©lĂ©ment suivant Ă  insĂ©rer dans
           la partie triée du tableau.
          Elle effectuera n - 1 itĂ©rations puisque le premier
           élément est déjà trié.
          Pour chaque Ă©lĂ©ment donnĂ© par la premiĂšre boucle,
           on fait un parcourt dans la partie triée pour
           déterminer son emplacement.
Exemples de calcul de la complexité
Exemple 1 : Tri par insertion
 Calcul de la complexitĂ©:
  ïź   Au meilleur des cas : le cas le plus favorable
      pour cet algorithme est quand le tableau est
      dĂ©jĂ  triĂ© (de taille n)  O(n)
  ïź   Au pire des cas : Le cas le plus dĂ©favorable
      pour cet algorithme est quand le tableau est
      inversement triĂ©  on fera une itĂ©ration pour
      le 1er élément, deux itérations pour le 2Úme et
      ainsi de suite pour les autres éléments.
      Soit 1+2+3+4+
+(n-1) = n(n + 1) − n
       sa complexitĂ© O(n2)          2
Exemples de calcul de la complexité
Exemple 1 : Tri par insertion
 Calcul de la complexitĂ©:
  ïź En moyenne des cas : En moyenne, la moitiĂ©
    des éléments du tableau sont triés, et sur
    l’autre moitiĂ© ils sont inversement triĂ©s.
    O(n2)
Exemples de calcul de la complexité
   Exemple 2 : Recherche dichotomique
Fonction RechDicho(Tab :Tableau, borneinf :entier, bornesup :entier,
elemcherche :entier) : entier
       Trouve = false ;
       Tant que ((non trouve) ET (borneinf<=bornesup)) faire
         mil = (borneinf+bornesup) DIV 2 ;
         Si (Tab[mil]=elemcherche) Alors
                  trouve=true ;
         Sinon
                  Si (elemcherche < Tab[mil]) Alors bornesup = mil-1 ;
                  Sinon    borneinf = mil+1 ;
                  Fin Si
         Fin Si
       Fin Tant que
       Si (trouve) Alors Retourner (mil) ;
       Sinon Retourner (-1) ;
       Fin Si
Fin
Exemples de calcul de la complexité
   Exemple 2 : Recherche dichotomique
   Cette fonction effectue une recherche dichotomique d'un
    élément dans un tableau trié. Supposons que le tableau est
    de taille n une puissance de 2 (n = 2q).
   Le pire des cas pour la recherche d'un Ă©lĂ©ment est de
    continuer les divisions jusqu'Ă  obtenir un tableau de taille 1.
   q le nombre d'itĂ©rations nĂ©cessaires pour aboutir Ă  un
    tableau de taille 1


                        derniĂšre itĂ©ration  taille tableau = 1




                                    La complexitĂ© = log2(n)
Chapitre 3 –
Les algorithmes de Tri
Tri par sélection
 Principe :
 Le principe est que pour classer n valeurs,
  il faut rechercher la plus petite valeur
  (resp. la plus grande) et la placer au
  début du tableau (resp. à la fin du
  tableau), puis la plus petite (resp. plus
  grande) valeur dans les valeurs restantes
  et la placer Ă  la deuxiĂšme position (resp.
  en avant derniĂšre position) et ainsi de
  suite...
Tri par sélection
   Algorithme :
i, j: entier ;
tmp, small : entier ;
t : tableau entier [n] ;
DĂ©but
     Pour i de 1 Ă  n-1 faire
           small←i;
           Pour j de i+1 Ă  n faire
                    Si t[j] < t[small] alors
                              small ←j ;
                    Fin si
           Fin pour
           tmp←t[small];
                                                T(n) = O(nÂČ)
           t[small] ←t[i];
           t[i] ← tmp;
     Fin pour
Fin
Tri par propagation / Ă  bulles
   Principe :
   Il consiste Ă  parcourir le tableau tab en permutant
    toute paire d'éléments consécutifs
    (tab[k],tab[k+1]) non ordonnés - ce qui est un
    échange et nécessite donc encore une variable
    intermédiaire de type entier. AprÚs le premier
    parcours, le plus grand élément se retrouve dans
    la derniĂšre case du tableau, en tab[N], et il reste
    donc Ă  appliquer la mĂȘme procĂ©dure sur le tableau
    composé des éléments tab[1], ..., tab[N-1].
Tri par propagation / Ă  bulles
   Algorithme :
 Procédure tri_Bulle (tab : tableau entier [N] ) i,
   k :entier ;tmp : entier ;
   Pour i de N Ă  2 faire
        Pour k de 1 Ă  i-1 faire
               Si (tab[k] > tab[k+1]) alors
                       tmp ← tab[k];
                       tab[k] ← tab[k+1];
                       tab[k+1] ← tmp;
               Fin si
        Fin pour                   T(n) = O(nÂČ)
   Fin pour
Fin
Chapitre 4 – La rĂ©cursivitĂ©
DĂ©finitions
   Un algorithme est dit rĂ©cursif s'il est dĂ©fini en
    fonction de lui-mĂȘme.
   La rĂ©cursion est un principe puissant permettant de
    définir une entité à l'aide d'une partie de celle-ci.
     Chaque appel successif travaille sur un ensemble
    d'entrées toujours plus affinée, en se rapprochant
    de plus en plus de la solution d'un problĂšme.
Evolution d’un appel rĂ©cursif
   L'exĂ©cution d'un appel rĂ©cursif passe par deux
    phases, la phase de descente et la phase de la
    remontée :
    ïź   Dans la phase de descente, chaque appel rĂ©cursif fait Ă 
        son tour un appel récursif. Cette phase se termine
        lorsque l'un des appels atteint une condition terminale.
         condition pour laquelle la fonction doit retourner une
        valeur au lieu de faire un autre appel récursif.
    ïź   Ensuite, on commence la phase de la remontĂ©e. Cette
        phase se poursuit jusqu'Ă  ce que l'appel initial soit
        terminé, ce qui termine le processus récursif.
Les types de récursivité
 1/ La récursivité simple :
  ïź   rĂ©cursivitĂ© simple  la fonction contient un seul appel
      récursif dans son corps.
  ïź   Exemple : la fonction factorielle
Les types de récursivité
  ïź   Trace d’exĂ©cution de la fonction factorielle (calcul de la
      valeur de 4!)
Les types de récursivité
 2/ La récursivité multiple:
  ïź   rĂ©cursivitĂ© multiple  la fonction contient plus d'un
      appel récursif dans son corps
  ïź   Exemple : le calcul du nombre de combinaisons en se
      servant de la relation de Pascal :
Les types de récursivité
 3/ La récursivité mutuelle:
  ïź   Des fonctions sont dites mutuellement rĂ©cursives si elles
      dépendent les unes des autres
  ïź   Par exemple la dĂ©finition de la paritĂ© d'un entier peut
      ĂȘtre Ă©crite de la maniĂšre suivante :
Les types de récursivité
 4/ La récursivité imbriquée:
  ïź   Exemple : La fonction d'Ackermann
Récursivité terminale vs. non terminale
   Une fonction rĂ©cursive est dite rĂ©cursive
    terminale si tous ses appels sont récursifs
    terminaux.
   Un appel rĂ©cursif est terminal s'il s'agit de la
    derniÚre instruction exécutée dans le corps d'une
    fonction et que sa valeur de retour ne fait pas
    partie d'une expression.
   Les    fonctions   rĂ©cursives     terminales    sont
    caractérisées par le fait qu'elles n'ont rien à faire
    pendant la phase de remontée
Importance de l’ordre des appels rĂ©cursifs
         Proc. terminale                     Proc. non terminale
Procédure AfficherGaucheDroite (           Procédure AfficherDroiteGauche (
   Tab : Tableau entier, N : entier,          Tab : Tableau entier, N : entier,
   i : entier)                                i : entier)
   Si (i<=N) Alors                            Si (i<=N) Alors
      Ecrire(Tab[i]) ;                           AfficherDroiteGauche (Tab,N,i+1) ;
      AfficherGaucheDroite (Tab,N,i+1) ;         Ecrire(Tab[i]) ;
      Fin Si                                     Fin Si
Fin                                        Fin

 l’ordre des appels rĂ©cursifs affecte la terminaison d’une
fonction récursive
Importance de l’ordre des appels rĂ©cursifs
Elimination de la récursivité
 DĂ©rĂ©cursiver, c’est transformer un
  algorithme récursif en un algorithme
  Ă©quivalent ne contenant pas des appels
  récursifs.
 Elimination de la rĂ©cursivitĂ© terminale
  simple
    ïź   Rappel : Un algorithme est dit rĂ©cursif terminal
        s’il ne contient aucun traitement aprùs un appel
        récursif.
    ïź   La rĂ©cursivitĂ© terminale simple peut ĂȘtre
        remplacée par une solution itérative.
Elimination de la récursivité terminale
simple
      Algo. récursif                       Algo. itératif
Procédure ALGOR(X)                 Procédure ALGOI(X)
   Si (COND) Alors                    Tant que (COND) faire
        TRAIT1                             TRAIT1
        ALGOR(ÎČ (X))                       X  ÎČ (X)
   Sinon                              Fin tant que
        TRAIT2                         TRAIT2
   Fin Si                          Fin
Fin
‱X est la liste des paramùtres ;
‱ COND est une condition portant sur X ;
‱ TRAIT1 est le traitement de base de l'algorithme (dĂ©pendant de X) ;
‱ ÎČ(X) reprĂ©sente la transformation des paramĂštres ;
‱ TRAIT2 est le traitement de terminaison (dĂ©pendant de X).
Application : a est diviseur de b ?
       Algo. récursif                   Algo. itératif
Fonction Diviseur (a,b) : Bool    Fonction Diviseur (a,b) : Bool
Si (a <=0) Alors                  Si (a <=0) Alors
   Retourner(Faux)                   Retourner(Faux)
Sinon                             Sinon
   Si (a>=b) Retourner (a=b)         Tant que (a<b) Faire
   Sinon                                  b  b-a
   Retourner (Diviseur (a,b-a))      Fin tant que
   Fin Si                            Retourner (a=b)
Fin Si                            Fin Si
Fin                               Fin
Elimination de la récursivité non
terminale simple
   Dans un algorithme rĂ©cursif non terminal, l’appel
    rĂ©cursif est suivi d’un traitement  il reste un
    traitement Ă  reprendre aprĂšs l’appel rĂ©cursif
   Il va falloir donc sauvegarder, sur une pile, le
    contexte de l’appel rĂ©cursif, typiquement les
    paramĂštres de l’appel engendrant l’appel rĂ©cursif.
     La rĂ©cursivitĂ© non terminale simple peut ĂȘtre
    remplacée par une solution itérative utilisant une
    pile.
Elimination de la récursivité non terminale
simple
     Algo. récursif          Algo. itératif
Procédure ALGOR(X)     Procédure ALGOI(X)
   Si (COND) Alors         Pile.init()
        TRAIT1            Tant que (COND) Faire
        ALGOR(ÎČ (X))           TRAIT1
        TRAIT2                 Pile.empiler(X)
   Sinon                       X  ÎČ (X)
        TRAIT3            Fin Tant que
   Fin Si                 TRAIT3
Fin                       Tant que (Non_vide_pile())
                          Faire
                               Pile.dépiler(U)
                               TRAIT2
                          Fin Tant que
                       Fin
Elimination de la récursivité non terminale
simple
     Algo. récursif                   Algo. itératif
Procédure                       Procédure ALGOI(X)
   AfficherDroiteGauche ( Tab       Pile.init()
   : Tableau entier, N :           Tant que (i<=N) Faire
   entier, i : entier)
                                        /* TRAIT1 */
   Si (i<=N) Alors
                                        Pile.empiler(Tab[i])
       AfficherDroiteGauche
                                        i  i+1
  (Tab,N,i+1) ;
       Ecrire(Tab[i]) ;            Fin Tant que
   Fin Si                          /* TRAIT3 */
Fin                                Tant que (Non_vide_pile())
                                   Faire
TRAIT1 = Ø
                                        Ecrire(Pile.dépiler() )
TRAIT2 = Ecrire(Tab[i])
                                          /* TRAIT2 */
TRAIT3 = Ø
                                   Fin Tant que
                                Fin
Exemple : Tours de Hanoi
   ProblĂšme :
    Le jeu est constituĂ© d’une plaquette de bois oĂč
    sont plantées trois tiges numérotées 1, 2 et 3.
    Sur ces tiges sont empilés des disques de
    diamÚtres tous différents. Les seules rÚgles du
    jeu sont que l’on ne peut dĂ©placer qu’un seul
    disque à la fois, et qu’il est interdit de poser un
    disque sur un disque plus petit.
    Au début, tous les disques sont sur la tige 1
    (celle de gauche), et Ă  la fin ils doivent ĂȘtre sur
    celle de droite.
Exemple : Tours de Hanoi
   RĂ©solution:
   On suppose que l’on sait
    résoudre le problÚme pour (n-1)
    disques. Pour déplacer n disques
    de la tige 1 vers la tige 3, on
    déplace les (n-1) plus petits
    disques de la tige 1 vers la tige
    2, puis on déplace le plus gros
    disque de la tige 1 vers la tige 3,
    puis on déplace les (n-1) plus
    petits disques de la tige 2 vers la
    tige 3.
Exemple : Tours de Hanoi
 Algorithme
Procédure Hanoi (n, départ, intermédiaire, destination)
   Si n > 0 Alors
        Hanoi (n-1, départ, destination, intermédiaire)
        déplacer un disque de départ vers destination
        Hanoi (n-1, intermédiaire, départ, destination)
   Fin Si
Fin
Exemple : Tours de Hanoi
 Trace d’exĂ©cution pour n=3
L’appel à Hanoi(3,1,2,3) entraüne l’affichage de :
1. DĂ©place un disque de la tige 1 vers la tige 3
2. DĂ©place un disque de la tige 1 vers la tige 2
3. DĂ©place un disque de la tige 3 vers la tige 2
4. DĂ©place un disque de la tige 1 vers la tige 3
5. DĂ©place un disque de la tige 2 vers la tige 1
6. DĂ©place un disque de la tige 2 vers la tige 3
7. DĂ©place un disque de la tige 1 vers la tige 3
Exemple : Tours de Hanoi
 Calcul de la complexitĂ© :
 On compte le nombre de dĂ©placements de
  disques effectuĂ©s par l’algorithme Hanoi
  invoqué sur n disques.
 On trouve :
    ïź T(n) = T(n-1) + 1 + T(n-1)
    ïź T(n) = 2T(n-1) + 1
     T(n) = 2n – 1
     ComplexitĂ© exponentielle
Paradigme « diviser pour régner »
   De nombreux algorithmes ont une structure rĂ©cursive: pour
    rĂ©soudre un problĂšme donnĂ©, ils s’appellent eux-mĂȘmes
    récursivement une ou plusieurs fois sur des problÚmes trÚs
    similaires, mais de tailles moindres, résolvent les sous
    problÚmes de maniÚre récursive puis combinent les
    résultats pour trouver une solution au problÚme initial.
   Le paradigme « diviser pour rĂ©gner » parcourt trois
    étapes à chaque appel récursif à savoir :
    ïź   Diviser : le problĂšme en un certain nombre de sous-
        problĂšmes de taille moindre ;
    ïź   RĂ©gner : sur les sous-problĂšmes en les rĂ©solvant d'une façon
        récursive ou le résoudre directement si la taille d'un sous-
        problÚme est assez réduite ;
    ïź   Combiner : les solutions des sous-problĂšmes en une solution
        globale pour le problĂšme initial.
Exemple 1
   Recherche de l’indice du maximum dans un tableau d’entiers
Fonction maximum ( Tab , indDeb, indFin)
Si ( indDeb = indFin) alors
    retourner (indDeb)
Sinon
    m=(indDeb+indFin)/2 // division du problĂšme en 2 sous-problĂšmes
    k1 = maximum (Tab, indDeb, m ) // régner sur le 1er sous-problÚme
    k2 = maximum (Tab, m+1, indFin)// régner sur le 2Úme sous-problÚme
    Si(Tab[k1] > Tab[k2]) Alors // combiner les solutions
          retourner (k1)
    Sinon
          retourner (k2)               T(n) = 2 T(n/2) + cte
    FinSi
FinSi
Fin
Exemple2 : multiplication de matrices carrées
   Dans cet exemple, on se propose de multiplier 2
    matrices carrées A et B de taille n * n chacune,
    oĂč n est une puissance exacte de 2. C est la
    matrice résultante.
   Si on dĂ©compose les matrices A, B et C en sous-
    matrices de taille n/2 * n/2, l'Ă©quation C = AB
    peut alors se réécrire :



   Le dĂ©veloppement de cette Ă©quation donne :
    r = ae+bf ; s = ag+bh; t = ce+df et u = cg+dh
Exemple2 : multiplication de matrices carrées
   Chacune de ces quatre opĂ©rations correspond Ă  :
    ïź   deux multiplications de matrices carrĂ©es de taille n/2
         2T(n/2)
    ïź   et une addition de telles matrices n2/4
   A partir de ces Ă©quations on peut dĂ©river un
    algorithme « diviser pour régner » dont la
    complexité est donnée par la récurrence :
     T(n) = 8T(n/2)+O(n2)
Analyse des algorithmes « Diviser pour Régner »
   On peut souvent donner une relation de rĂ©currence qui dĂ©crit
    le temps d'exĂ©cution d’un algorithme « diviser pour rĂ©gner »
    en fonction des temps d'exécution des appels récursifs
    résolvant les sous-problÚmes associés de taille moindre.
   Cette rĂ©currence se dĂ©compose suivant les trois Ă©tapes du
    paradigme de base :
    ïź   Si la taille du problĂšme est suffisamment rĂ©duite, n ≀ c pour
        une certaine constante c, la résolution est directe et consomme
        un temps constant O(1).
    ïź   Sinon, on divise le problĂšme en a sous-problĂšmes chacun de
        taille 1/b de la taille du problÚme initial. Le temps d'exécution
        total se décompose alors en trois parties :
            D(n) : le temps nĂ©cessaire Ă  la division du problĂšme en sous-
             problĂšmes.
            aT (n/b) : le temps de rĂ©solution des a sous-problĂšmes.
            C(n) : le temps nĂ©cessaire pour construire la solution finale Ă  partir
             des solutions aux sous-problĂšmes.
Analyse des algorithmes « Diviser pour Régner »
   La relation de rĂ©currence prend alors la forme :




   Soit la fonction f (n) la fonction qui regroupe D(n)
    et C(n). La fonction T(n) est alors définie :
                 T(n) = a.T(n / b) + f (n)
                T (n) = a.T (n / b) + c.nk
Résolution des récurrence des algorithmes
« Diviser pour Régner »
   ThĂ©orĂšme de rĂ©solution de la rĂ©currence :
    ïź   si a > bk  T(n) = O(nlogb a )
    ïź   si a = bk  T(n) = O(nk logbn)
    ïź   si a < bk  T(n) = O( f (n)) = O(nk )
   RĂ©solution de la relation de rĂ©currence pour
    l’exemple de la multiplication de matrices :
    ïź   T(n) = 8 T(n/2) + O(n2)
    ïź   a = 8 , b = 2, k = 2  a > bk
       Logba = 3
       T(n) = O(n3)
Analyse des algorithmes « Diviser pour Régner »
   ComplexitĂ© de l’algorithme de recherche du
    maximum: T(n) = 2 T(n/2) + 3
    ïź   a = 2 , b = 2, k = 0  a > bk
       Logba = 1
       T(n) = O(n)
Application : algorithme de recherche dichotomique
Fonction RechDicho(Tab :Tableau, borneinf :entier, bornesup :entier,
elem :entier) : bool

    Si (borneinf<=bornesup) alors
         mil = (borneinf+bornesup) DIV 2 ;
         Si (Tab[mil]=elem) Alors
                  retourner (vrai)
         Sinon
                  Si (Tab[mil]>elem) Alors
                          Retourner (RechDicho(Tab, borneinf, mil-1, elem))
                  Sinon
                          Retourner(RechDicho(Tab, mil+1, bornesup, elem))
                  Fin Si
         Fin Si
    Sinon
         Retourner (Faux)
    FinSi
Application : algorithme de recherche dichotomique
   Analyse de la complexitĂ© :
    ïź   T(n) = T(n/2) + cte
    ïź   a = 1 , b = 2, k = 0  a = bk
       a = bk  T(n) = O(nk logbn)
       T(n) = O(log2n)
Exemples d’application
                                 ïŁ«nïŁ¶
 Exemple 1 :         T (n) = 9T ïŁŹ ïŁ· + n
   ïź a = 9 , b = 3 , k = 1
                                 ïŁ­3ïŁž
     a > bk
     Logba = 2
     T(n) = O(nÂČ)
                                 ïŁ« 2n ïŁ¶
   Exemple 2 :       T ( n) = T ïŁŹ ïŁ· + 1
                                 ïŁ­ 3 ïŁž
    ïź a = 1 , b = 3/2 , k = 0
     a = bk
     T(n) = O(nklogn) = O(logn)
Exemples d’application
                               ïŁ«nïŁ¶
 Exemple 3 :       T (n) = 3T ïŁŹ ïŁ· + n log n
   ïź a = 3 , b = 4 , k = ??
                               ïŁ­4ïŁž
   or n < nlogn < nÂČ ïƒš1 < k < 2
    4 < bk < 16  a < bk
    T(n) = O(f(n)) = O(n logn)
Autres résolutions de récurrence
   Equations de rĂ©currence linĂ©aires:
                                            ïŁ«           n
                                                           f (i ) ïŁ¶
 T (n) = aT (n − 1) + f (n )   T ( n ) = a ïŁŹ T ( 0) + ∑ i ïŁ·
                                          n

                                            ïŁ­         i =1 a      ïŁž
 Exemple : Les Tours de Hanoi
                                    ïŁ«    n
                                           1ïŁ¶
 T(n) = 2 T(n-1) + 1  T ( n) = 2 ïŁŹ 0 + ∑ i ïŁ· = 2 − 1
                                  n               n

                                           ïŁ­      i =1   2 ïŁž
Autres résolutions de récurrence
   Equations de rĂ©currence linĂ©aires sans second
    membre (f(n) = cte)
    T (n) − a1T (n − 1) − a2T (n − 2 ) − ... − ak T (n − k ) = cte
   A une telle Ă©quation, on peut associer un
    polynîme: P ( x) = x k − a x k −1 − a x k − 2 − ... − a
                              1          2                  k
   La rĂ©solution de ce polynĂŽme nous donne m
    racines ri ( avec m<=k).
   La solution de l’équation de rĂ©currence est ainsi
    donnée par :
                       T (n) = c1r1 + c2 r2 + c3 r3 + ... + c r
                               n          n            n               n
                                                                     m m

 Cette solution est en gĂ©nĂ©ral exponentielle
Autres résolutions de récurrence
   Exemple : La suite de Fibonacci



   T(n) = T(n-1) + T(n-2)
   On pose P(x) = XÂČ - X – 1
     r = 1 + 5 et r = 1 − 5
         1                2
                2                2 ïŁ« 1 + 5 ïŁ¶n   ïŁ«1− 5 ïŁ¶
                                                          n

           T (n) = a r1n + b r2n = a ïŁŹ     ïŁ·
                                     ïŁŹ 2 ïŁ· +b
                                                ïŁŹ
                                                ïŁŹ 2 ïŁ·
                                                      ïŁ·
    
                                     ïŁ­     ïŁž    ïŁ­     ïŁž
                     ïŁ« ïŁ« 1 + 5 ïŁ¶n ïŁ¶
          T (n) = ÎŸïŁŹ ïŁŹ         ïŁ· ïŁ·
                     ïŁŹïŁŹ 2 ïŁ· ïŁ·
                     ïŁ­ïŁ­         ïŁž ïŁž
Suite du chapitre 3 –
Les algorithmes de Tri
Tri par fusion
 Principe :
 Le principe du tri par fusion est plutĂŽt
  simple. On dit que trier un tableau de
  taille N, c'est trier deux tableaux de taille
  N/2; une fois les deux tableaux triés on
  n’a plus qu'Ă  les rĂ©unir (les fusionner) de
  sorte à ce que le tableau final soit trié. Ce
  tri bien sûr utilise une notion de
  récursivité (un tableau étant la somme de
  deux tableaux).
Tri par fusion
 Algorithme :
 Fonction tri_fusion (T, deb, fin) : tableau entier
  T1, T2 : tableau entier [N/2] ;
  Si (deb >= fin) alors
       Retourner T ;
  Sinon
       mil = (deb + fin) DIV 2;
       T1 = tri_fusion (T, deb, mil) ;
       T2 = tri_fusion (T, mil+1, fin)) ;
       Retourner fusion (T1, T2) ;
  Fin si
FIN
                          T(n) = 2 T(n/2) + Tfusion(n)
Tri par fusion
Fonction fusion (T1, T2) : tableau entier
   T1 : tableau entier [1...N] ; T2 : tableau entier [1...M] ;
   T: tableau entier [1...M+N] ;
   i, j: entier; i←1 ;j←1 ;
   Tantque (i+j-1 <> N+M) faire
          Si (i ≀ N) alors
                    si (j ≀ M) alors
                              si (T1[i] < T2[j]) alors
                                        T[i+j-1]←T1[i] ; i←i+1 ;

                            sinon
                                     T[i+j-1]←T2[j] ; j←j+1 ;
                            Fin si
                  sinon
                            T[i+j-1]←T1[i];   i←i+1;
                  Fin si
        sinon                    T[i+j-1]←T2[j] ;
        j←j+1 ;         Fin si
   FinTanque    Retourner T ;FIN                         Tfusion(n) = O(n)
Tri par fusion
    L’algorithme Tri_Fusion est de type « diviser pour
    régner ». Il faut donc étudier ses trois phases:
   Diviser : cette Ă©tape se rĂ©duit au calcul du milieu
    de l’intervalle [deb,fin], sa complexitĂ© est donc
    en O(1).
   RĂ©gner : l’algorithme rĂ©sout rĂ©cursivement deux
    sous-problĂšmes de tailles respectives (n/2) , d’oĂč
    une complexité en 2T(n/2).
   Combiner : la complexitĂ© de cette Ă©tape est celle
    de l’algorithme de fusion qui est de O(n) pour la
    construction d’un tableau solution de taille n.
Tri par fusion
   T(n) = 2 T(n/2) + O(n)
   Rappel : ThĂ©orĂšme de rĂ©solution de la rĂ©currence
    T(n) = a T(n/b) + O(nk):
    ïź   si a > bk  T(n) = O(nlogb a )
    ïź   si a = bk  T(n) = O(nk logbn)
    ïź   si a < bk  T(n) = O( f (n)) = O(nk )
a  = 2, b = 2, k = 1 (2Ăšme cas)
 T(n) = O(n log2n)
Tri rapide (Quicksort)
   Principe :
    Le tri rapide est fondé sur le paradigme « diviser pour
    régner», tout comme le tri par fusion, il se décompose donc
    en trois Ă©tapes :
   Diviser : Le tableau T[deb..fin] est partitionnĂ© (et
    réarrangé) en deux sous-tableaux non vides, T[deb..inter] et
    T[inter+1..fin] tels que chaque élément de T[deb..fin] soit
    inférieur ou égal à chaque élément de T[inter+1..fin].
    L’indice inter est calculĂ© pendant la procĂ©dure de
    partitionnement.
   RĂ©gner : Les deux sous-tableaux T[deb..inter] et
    T[inter+1..fin] sont triés par des appels récursifs.
   Combiner : Comme les sous-tableaux sont triĂ©s sur place,
    aucun travail n’est nĂ©cessaire pour les recombiner, le tableau
    T[deb..fin] est déjà trié !
Tri rapide
Tri_Rapide (T, deb, fin)
Si (deb < fin ) alors
    inter =Partionner (T, deb, fin)
    Tri_Rapide (T, deb, inter)
    Tri_Rapide (T, inter+1, fin)
Fin si
Partionner (T, deb, fin)
x = T(deb)
i = deb-1 ; j= fin+1
Tant que (1)
RĂ©pĂ©ter { j=j-1 } Jusqu’à T(j) <= x
RĂ©pĂ©ter { i =i+1 } Jusqu’à T(i) >= x
si ( i < j )
permuter (T(i), T(j))
sinon retourner j Fin Si
Fin
Tri rapide : calcul de la complexité
   Pire cas
    Le cas pire intervient quand le partitionnement produit une région
    à n-1 éléments et une à 1 élément.
    Comme le partitionnement coûte O(n) et que T(1) = O(1), la
    rĂ©currence pour le temps d’exĂ©cution est : T(n) = T(n-1) +O(n)
    et par sommation on obtient : T(n) = O(nÂČ)
   Meilleur cas :
    Le meilleur cas intervient quand le partitionnement produit deux
    régions de longueur n/2.
    La récurrence est alors définie par : T(n) = 2T(n / 2) + O(n)
    ce qui donne d’aprĂšs le thĂ©orĂšme de rĂ©solution des rĂ©currences :
    T(n) = O(nlog n)
Chapitre 5 –
Graphes et arbres
Les graphes
   Un graphe orientĂ© G est reprĂ©sentĂ© par un couple
    (S, A) oĂč S est un ensemble fini et A une relation
    binaire sur S. L’ensemble S est l’ensemble des
    sommets de G et A est l’ensemble des arcs de G.
   Il existe deux types de graphes :
    ïź   graphe orientĂ© : les relations sont orientĂ©es et on parle d’arc. Un
        arc est représenté par un couple de sommets ordonnés.
    ïź   Graphe non orientĂ© : les relations ne sont pas orientĂ©es et on
        parle alors d’arĂȘtes.
        Une arĂȘte est reprĂ©sentĂ©e par une paire de sommets non
        ordonnés.
Les graphes
   Une boucle est un arc qui relie un sommet Ă  lui-mĂȘme. Dans un
    graphe non orientĂ© les boucles sont interdites et chaque arĂȘte est
    donc constituée de deux sommets distincts.
   DegrĂ© d’un sommet : Dans un graphe non orientĂ©, le degrĂ© d’un
    sommet est le nombre d’arĂȘtes qui lui sont incidentes. Si un
    sommet est de degré 0, il est dit isolé.
   DegrĂ© sortant d’un sommet : Dans un graphe orientĂ©, le degrĂ©
    sortant d’un sommet est le nombre d’arcs qui en partent,
   DegrĂ© rentrant d’un sommet : le degrĂ© entrant est le nombre
    d’arcs qui y arrivent et le degrĂ© est la somme du degrĂ© entrant et
    du degré sortant.
   Chemin : Dans un graphe orientĂ© G = (S,A), un chemin de
    longueur k d’un sommet u Ă  un sommet v est une sĂ©quence
    (u0,u1,
, uk) de sommets telle que u = u0, v = uk et (ui-1, ui)
    appartient Ă  A pour tout i.
    Un chemin est élémentaire si ses sommets sont tous distincts
Les graphes
   Un sous-chemin p0 d’un chemin p = (u0,u1, 
. ,uk) est une sous-
    séquence contiguë de ses sommets. Autrement dit, il existe i et j,
    0<=i<= j <=k, tels que p0 = (ui,ui+1, 
. ,uj).
   Circuit : Dans un graphe orientĂ© G=(S,A), un chemin (u0,u1, 
.
    ,uk) forme un circuit si u0 =uk et si le chemin contient au moins un
    arc. Ce circuit est élémentaire si les sommets u0, ..., uk sont
    distincts. Une boucle est un circuit de longueur 1.
   Cycle : Dans un graphe non orientĂ© G = (S,A), une chaĂźne
    (u0,u1,
., uk) forme un cycle si k >= 2 et si u0 = uk. Ce cycle est
    élémentaire si les sommets u0, ..., uk sont distincts. Un graphe
    sans cycle est dit acyclique.
   Sous-graphe : On dit qu’un graphe G0 = (S0,A0) est un sous-
    graphe de G = (S,A) si S0 est inclus dans S et si A0 est inclus
    dans A.
Les arbres
   PropriĂ©tĂ©s des arbres :
    Soit G = (S,A) un graphe non orienté. Les affirmations
    suivantes sont Ă©quivalentes.
    ïź   1. G est un arbre.
    ïź   2. Deux sommets quelconques de G sont reliĂ©s par un unique
        chemin élémentaire.
    ïź   3. G est acyclique et |A| = |S| - 1
    ïź   4. G est acyclique, mais si une arĂȘte quelconque est ajoutĂ©e Ă 
        A, le graphe résultant contient un cycle.
Arbres – dĂ©finitions
   Arbre enracinĂ© (ou arborescence): C’est un arbre dans
    lequel l’un des sommets se distingue des autres. On appelle
    ce sommet la racine. Ce sommet particulier impose en
    rĂ©alitĂ© un sens de parcours de l’arbre
   AncĂȘtre : Soit x un noeud (ou sommet) d’un arbre A de
    racine r. Un noeud quelconque y sur l’unique chemin allant
    de r Ă  x est appelĂ© ancĂȘtre de x.
   PĂšre et fils : Si (y,x) est un arc alors y est le pĂšre de x et
    x est le fils de y. La racine est le seul noeud qui n’a pas de
    pĂšre.
   Feuille ou noeud externe (ou terminal) : Une feuille est
    un noeud sans fils. Un noeud qui n’est pas une feuille est
    un noeud interne.
   Sous-arbre : Le sous-arbre de racine x est l’arbre composĂ©
    des descendants de x, enraciné en x.
Arbres - définitions
   DegrĂ© d’un nƓud : Le nombre de fils du nƓud x est
    appelé le degré de x.
   Profondeur d’un nƓud : La longueur du chemin entre la
    racine r et le nƓud x est la profondeur de x.
   Profondeur de l’arbre : c’est la plus grande profondeur
    que peut avoir un nƓud quelconque de l’arbre. Elle est dite
    aussi la hauteur de l’arbre.
   Arbre binaire : c’est un arbre dont chaque nƓud a au plus
    deux fils.
   Arbre binaire complet : Dans un arbre binaire complet
    chaque nƓud est soit une feuille, soit de degrĂ© deux. Aucun
    nƓud n’est donc de degrĂ© 1.
Parcours des arbres
   Parcours en profondeur
   Dans un parcours en profondeur, on descend d’abord le
    plus profondĂ©ment possible dans l’arbre puis, une fois
    qu’une feuille a Ă©tĂ© atteinte, on remonte pour explorer les
    autres branches en commençant par la branche « la plus
    basse » parmi celles non encore parcourues. Les fils d’un
    nƓud sont bien Ă©videmment parcourus suivant l’ordre sur
    l’arbre.
   Algorithme:
    Algorithme ParPro(A)
       si A n’est pas rĂ©duit Ă  une feuille alors
         Pour tous les fils u de racine(A) Faire
                   ParPro(u)
         Fin pour
       finSi
    Fin
Parcours des arbres
   Parcours en largeur
   Dans un parcours en largeur, tous les nƓuds Ă  une
    profondeur i doivent avoir été visités avant que le premier
    nƓud Ă  la profondeur i+1 ne soit visitĂ©. Un tel parcours
    nĂ©cessite l’utilisation d’une file d’attente pour se souvenir
    des branches qui restent Ă  visiter.
   Algorithme:
    Algorithme Parcours_Largeur(A)
       F : File d’attente
       F.enfiler(racine(A))
       Tant que F != vide Faire
                   u=F.défiler()
                   Afficher (u)
                   Pour « chaque fils v de » u Faire
                             F.enfiler (v)
                   FinPour
       Fin Tant que
    Fin
Parcours des graphes
   Le parcours des graphes est un peu plus compliquĂ© que
    celui des arbres. En effet, les graphes peuvent contenir des
    cycles et il faut éviter de parcourir indéfiniment ces cycles.
    Pour cela, il suffit de colorier les sommets du graphe.
    ïź   Initialement les sommets sont tous blancs,
    ïź   lorsqu’un sommet est rencontrĂ© pour la premiĂšre fois il est
        peint en gris,
    ïź   lorsque tous ses successeurs dans l’ordre de parcours ont Ă©tĂ©
        visités, il est repeint en noir.
Parcours des graphes
Algorithme Pacours_Profondeur (G)      Algorithme VisiterPP(G, s)
    Pour chaque sommet u de G Faire       couleur[s]=Gris
         couleur[u]=Blanc                 Pour chaque voisin v de s Faire
    FinPour                               Si couleur[v] = Blanc alors
    Pour chaque sommet u de G Faire             VisiterPP(G, v)
         si couleur[u] = Blanc alors      FinSi
               VisiterPP(G, u)            FinPour
         FinSi                            couleur[s]=Noir
    FinPour
Fin                                    Fin
Parcours des graphes
Algorithme Parcours_Largeur(G, s)
   F : File d’attente
   Pour chaque sommet u de G Faire
         couleur[u] = Blanc
   FinPour
   couleur[s]=Gris
   F.enfiler(s)
   Tant que F != Vide Faire
         u=F.défiler()
         Pour chaque voisin v de u Faire
                  Si couleur(v) = Blanc alors
                          couleur(v)= Gris
                          F.enfiler(v)
         FinPour
         Couleur(u)= Noir
FinTant que
Chapitre 6 –
Arbres binaires de
   recherche
DĂ©finitions
 Un arbre binaire est un graphe qui admet une racine et
  sans cycle et dont chaque nƓud admet deux fils : fils droit
  et fils gauche.
 Structure de donnĂ©es :
Enregistrement NƓud
{
  Info : Type (entier, réel, chaine, 
)
  FilsG : ^ NƓud
  FilsD : ^ NƓud
}
Racine : ^NƓud
 Il existe 3 mĂ©thodes de parcours d’un arbre binaire :
    ïź   parcours prĂ©fixe : pĂšre, fils gauche, fils droit
    ïź   parcours infixe : fils gauche, pĂšre, fils droit
    ïź   parcours postfixe : fils gauche, fils droit, pĂšre
Parcours préfixé
Algorithme PrĂ©fixe(racine : ^NƓud)

Si (racine != Nil) Alors
  AfficheRacine(racine)
  Préfixe (racine^.FilsG)
  Préfixe (racine^.FilsD)
FinSi
Fin
Parcours préfixé utilisant une pile
   Le programme suivant est une version dĂ©rĂ©cursivĂ©e
    utilisant une pile explicite et permettant le parcours préfixé
    d’un arbre binaire.
Algorithme PrĂ©fixe (racine : ^NƓud)
  P : pile
  Empiler (P, racine)
  Tant que (Non_Vide(P))
      racine = depiler (P)
      Empiler (P,racine^.FilsD)
      Empiler (P,racine^.FilsG)
  Fin Tant que
Fin
Parcours infixé
Algorithme infixe(racine : ^NƓud)

Si (racine != Nil) Alors
  infixe (racine^.FilsG)
  AfficheRacine(racine)
  infixe (racine^.FilsD)
FinSi
Fin
Parcours postfixé
Algorithme Postfixe(racine : ^NƓud)

Si (racine != Nil) Alors
  Postfixe (racine^.FilsG)
  Postfixe (racine^.FilsD)
  AfficheRacine(racine)
FinSi
Fin
Arbre binaire de recherche
   Un arbre binaire de recherche est un arbre binaire dans
    lequel chaque nƓud est supĂ©rieur Ă  son fils gauche et
    infĂ©rieur Ă  son fils droit et il n’y a pas de nƓuds Ă©gaux.
   Un arbre binaire de recherche est intĂ©ressant puisqu’il est
    toujours possible de connaĂźtre dans quelle branche de
    l’arbre se trouve un Ă©lĂ©ment et de proche en proche le
    localiser dans l’arbre. On peut aussi utiliser un arbre binaire
    de recherche pour ordonner une liste d’élĂ©ments.
Recherche dans un arbre binaire de recherche
Algorithme Chercher (racine : ^NƓud , X : Ă©lĂ©ment)
    Si ( racine = Nil) alors
          retourner 0
    Sinon
          Si( racine^.info = X ) alors
                   retourner 1
          Else
                   Si (X < racine^.info ) alors
                           retourner Chercher(racine^.FilsG, X)
                   Else
                           retourner Chercher (racine^.FilsD, X)
                   Finsi
          FinSi
    FinSi
Fin
Insertion dans un arbre binaire de recherche
   L’élĂ©ment Ă  ajouter est insĂ©rĂ© lĂ  oĂč on l’aurait trouvĂ© s’il avait
    Ă©tĂ© prĂ©sent dans l’arbre. L’algorithme d’insertion recherche
    donc l’élĂ©ment dans l’arbre et, quand il aboutit Ă  la conclusion
    que l’élĂ©ment n’appartient pas Ă  l’arbre (il aboutit Ă  la terre),
    il insĂšre l’élĂ©ment comme fils du dernier nƓud visitĂ©.
Algorithme InsĂ©rer (racine : ^NƓud, X : Ă©lĂ©ment )
    Si (racine = nil) alors
          « ajouter un nƓud pour X Ă  cet endroit»
    Sinon
          Si (racine^.info = X)
                   Ecrire ("l’élĂ©ment Ă  insĂ©rer existe dĂ©jĂ  dans l’arbre")
          Sinon
                   Si (X> racine^.info)
                            Insérer (racine^.FD, X)
                   Sinon
                            Insérer (racine^.FG, X)
Fin
Suppression dans un arbre binaire de recherche


   1er cas : l’élĂ©ment Ă  supprimer n’a pas de
    fils  il est terminal et il suffit de le
    supprimer
Suppression dans un arbre binaire de recherche

   2Ăšme cas : l’élĂ©ment a un fils unique  on
    supprime le nƓud et on relie son fils à
    son pĂšre
Suppression dans un arbre binaire de recherche

   3Ăšme cas : l’élĂ©ment Ă  supprimer a deux
    fils  on le remplace par son successeur
    qui est toujours le minimum de ses
    descendants droits.
Merci pour votre attention !

Weitere Àhnliche Inhalte

Was ist angesagt?

récursivité algorithmique et complexité algorithmique et Les algorithmes de tri
récursivité algorithmique et complexité algorithmique et Les algorithmes de trirécursivité algorithmique et complexité algorithmique et Les algorithmes de tri
récursivité algorithmique et complexité algorithmique et Les algorithmes de triYassine Anddam
 
TD1-UML-correction
TD1-UML-correctionTD1-UML-correction
TD1-UML-correctionLilia Sfaxi
 
TP2-UML-Correction
TP2-UML-CorrectionTP2-UML-Correction
TP2-UML-CorrectionLilia Sfaxi
 
TD2 - UML - Correction
TD2 - UML - CorrectionTD2 - UML - Correction
TD2 - UML - CorrectionLilia Sfaxi
 
Chapitre 5 arbres binaires
Chapitre 5 arbres binairesChapitre 5 arbres binaires
Chapitre 5 arbres binairesSana Aroussi
 
Cours systÚmes temps réel partie 1 Prof. Khalifa MANSOURI
Cours  systÚmes temps réel partie 1 Prof. Khalifa MANSOURICours  systÚmes temps réel partie 1 Prof. Khalifa MANSOURI
Cours systÚmes temps réel partie 1 Prof. Khalifa MANSOURIMansouri Khalifa
 
cours de complexité algorithmique
cours de complexité algorithmiquecours de complexité algorithmique
cours de complexité algorithmiqueAtef MASMOUDI
 
Fascicule tp programmation c
Fascicule tp programmation cFascicule tp programmation c
Fascicule tp programmation cMissaoui Abdelbaki
 
Methodes d'accÚs dans les réseaux locaux
Methodes d'accÚs dans les réseaux locauxMethodes d'accÚs dans les réseaux locaux
Methodes d'accÚs dans les réseaux locauxInes Kechiche
 
Gestion des threads
Gestion des threadsGestion des threads
Gestion des threadsSana Aroussi
 
Curriculum informatique 2Úme année Septembre 2019
Curriculum informatique 2Úme année Septembre 2019Curriculum informatique 2Úme année Septembre 2019
Curriculum informatique 2Úme année Septembre 2019Amine Ellouze
 
La complexité des algorithmes récursives Géométrie algorithmique
La complexité des algorithmes récursivesGéométrie algorithmiqueLa complexité des algorithmes récursivesGéométrie algorithmique
La complexité des algorithmes récursives Géométrie algorithmiqueHajer Trabelsi
 
Algorithme & structures de données Chap I
Algorithme & structures de données Chap IAlgorithme & structures de données Chap I
Algorithme & structures de données Chap IInes Ouaz
 
cours algorithme et structure de données 1er année
cours algorithme et structure de données 1er annéecours algorithme et structure de données 1er année
cours algorithme et structure de données 1er annéeMissaoui Abdelbaki
 
Les formes de l’évaluation en informatique scolaire fĂ©vrier2014
Les formes de l’évaluation en informatique scolaire fĂ©vrier2014Les formes de l’évaluation en informatique scolaire fĂ©vrier2014
Les formes de l’évaluation en informatique scolaire fĂ©vrier2014Haddi Abderrahim
 
Chapitre 1 arbres de recherche
Chapitre 1 arbres de rechercheChapitre 1 arbres de recherche
Chapitre 1 arbres de rechercheSana Aroussi
 
Introduction aux systÚmes répartis
Introduction aux systÚmes répartisIntroduction aux systÚmes répartis
Introduction aux systÚmes répartisHeithem Abbes
 
Algorithmique et Structures de Données II
Algorithmique et Structures de Données IIAlgorithmique et Structures de Données II
Algorithmique et Structures de Données IIRiadh Bouslimi
 
SystĂšmes d'Exploitation - chp3-gestion mémoire
SystĂšmes d'Exploitation - chp3-gestion mémoireSystĂšmes d'Exploitation - chp3-gestion mémoire
SystĂšmes d'Exploitation - chp3-gestion mémoireLilia Sfaxi
 
Chapitre 3 NP-complétude
Chapitre 3 NP-complétudeChapitre 3 NP-complétude
Chapitre 3 NP-complétudeSana Aroussi
 

Was ist angesagt? (20)

récursivité algorithmique et complexité algorithmique et Les algorithmes de tri
récursivité algorithmique et complexité algorithmique et Les algorithmes de trirécursivité algorithmique et complexité algorithmique et Les algorithmes de tri
récursivité algorithmique et complexité algorithmique et Les algorithmes de tri
 
TD1-UML-correction
TD1-UML-correctionTD1-UML-correction
TD1-UML-correction
 
TP2-UML-Correction
TP2-UML-CorrectionTP2-UML-Correction
TP2-UML-Correction
 
TD2 - UML - Correction
TD2 - UML - CorrectionTD2 - UML - Correction
TD2 - UML - Correction
 
Chapitre 5 arbres binaires
Chapitre 5 arbres binairesChapitre 5 arbres binaires
Chapitre 5 arbres binaires
 
Cours systÚmes temps réel partie 1 Prof. Khalifa MANSOURI
Cours  systÚmes temps réel partie 1 Prof. Khalifa MANSOURICours  systÚmes temps réel partie 1 Prof. Khalifa MANSOURI
Cours systÚmes temps réel partie 1 Prof. Khalifa MANSOURI
 
cours de complexité algorithmique
cours de complexité algorithmiquecours de complexité algorithmique
cours de complexité algorithmique
 
Fascicule tp programmation c
Fascicule tp programmation cFascicule tp programmation c
Fascicule tp programmation c
 
Methodes d'accÚs dans les réseaux locaux
Methodes d'accÚs dans les réseaux locauxMethodes d'accÚs dans les réseaux locaux
Methodes d'accÚs dans les réseaux locaux
 
Gestion des threads
Gestion des threadsGestion des threads
Gestion des threads
 
Curriculum informatique 2Úme année Septembre 2019
Curriculum informatique 2Úme année Septembre 2019Curriculum informatique 2Úme année Septembre 2019
Curriculum informatique 2Úme année Septembre 2019
 
La complexité des algorithmes récursives Géométrie algorithmique
La complexité des algorithmes récursivesGéométrie algorithmiqueLa complexité des algorithmes récursivesGéométrie algorithmique
La complexité des algorithmes récursives Géométrie algorithmique
 
Algorithme & structures de données Chap I
Algorithme & structures de données Chap IAlgorithme & structures de données Chap I
Algorithme & structures de données Chap I
 
cours algorithme et structure de données 1er année
cours algorithme et structure de données 1er annéecours algorithme et structure de données 1er année
cours algorithme et structure de données 1er année
 
Les formes de l’évaluation en informatique scolaire fĂ©vrier2014
Les formes de l’évaluation en informatique scolaire fĂ©vrier2014Les formes de l’évaluation en informatique scolaire fĂ©vrier2014
Les formes de l’évaluation en informatique scolaire fĂ©vrier2014
 
Chapitre 1 arbres de recherche
Chapitre 1 arbres de rechercheChapitre 1 arbres de recherche
Chapitre 1 arbres de recherche
 
Introduction aux systÚmes répartis
Introduction aux systÚmes répartisIntroduction aux systÚmes répartis
Introduction aux systÚmes répartis
 
Algorithmique et Structures de Données II
Algorithmique et Structures de Données IIAlgorithmique et Structures de Données II
Algorithmique et Structures de Données II
 
SystĂšmes d'Exploitation - chp3-gestion mémoire
SystĂšmes d'Exploitation - chp3-gestion mémoireSystĂšmes d'Exploitation - chp3-gestion mémoire
SystĂšmes d'Exploitation - chp3-gestion mémoire
 
Chapitre 3 NP-complétude
Chapitre 3 NP-complétudeChapitre 3 NP-complétude
Chapitre 3 NP-complétude
 

Andere mochten auch

Habilidades gerenciales
Habilidades gerencialesHabilidades gerenciales
Habilidades gerencialesMarco Trujillo
 
Como se mide la vida
Como se mide la vidaComo se mide la vida
Como se mide la vidaLUZ M.
 
Sigo en pie (jorge luis borges)
Sigo en pie (jorge  luis borges)Sigo en pie (jorge  luis borges)
Sigo en pie (jorge luis borges)LUZ M.
 
Guiaseguridadenellaboratorio brian lugo barona
Guiaseguridadenellaboratorio brian lugo baronaGuiaseguridadenellaboratorio brian lugo barona
Guiaseguridadenellaboratorio brian lugo baronaBrian Barona
 
Perlas al corazon
Perlas al corazonPerlas al corazon
Perlas al corazonLUZ M.
 
Resumen recomendaciones papps 2014
Resumen recomendaciones papps 2014Resumen recomendaciones papps 2014
Resumen recomendaciones papps 2014fcamarelles
 
Cie 9 Avantages Maison
Cie 9 Avantages MaisonCie 9 Avantages Maison
Cie 9 Avantages MaisonEco_innovation
 
Aceptacion
AceptacionAceptacion
AceptacionLUZ M.
 
Revista de computacion
Revista de computacionRevista de computacion
Revista de computacionRuben Hidalgo
 
Alejandro Magno
Alejandro MagnoAlejandro Magno
Alejandro MagnoLUZ M.
 
Webassadors - Mixology #4 - Actu' Web de la semaine du 28.07.14
Webassadors - Mixology #4 - Actu' Web de la semaine du 28.07.14Webassadors - Mixology #4 - Actu' Web de la semaine du 28.07.14
Webassadors - Mixology #4 - Actu' Web de la semaine du 28.07.14Webassadors
 
Dossier de presse BCV (dtp 83)
Dossier de presse BCV (dtp 83)Dossier de presse BCV (dtp 83)
Dossier de presse BCV (dtp 83)Jezabel Roullee
 
Redes sociales
Redes socialesRedes sociales
Redes socialescarolina153
 
Una buena reflexion
Una buena reflexionUna buena reflexion
Una buena reflexionLUZ M.
 
Cuales son los detonantes para que se conviertan en hikikomoris
Cuales son los detonantes para que se conviertan en hikikomorisCuales son los detonantes para que se conviertan en hikikomoris
Cuales son los detonantes para que se conviertan en hikikomorisAdilene Moya
 

Andere mochten auch (20)

Habilidades gerenciales
Habilidades gerencialesHabilidades gerenciales
Habilidades gerenciales
 
Como se mide la vida
Como se mide la vidaComo se mide la vida
Como se mide la vida
 
Sigo en pie (jorge luis borges)
Sigo en pie (jorge  luis borges)Sigo en pie (jorge  luis borges)
Sigo en pie (jorge luis borges)
 
Tor1
Tor1Tor1
Tor1
 
Guiaseguridadenellaboratorio brian lugo barona
Guiaseguridadenellaboratorio brian lugo baronaGuiaseguridadenellaboratorio brian lugo barona
Guiaseguridadenellaboratorio brian lugo barona
 
Perlas al corazon
Perlas al corazonPerlas al corazon
Perlas al corazon
 
Resumen recomendaciones papps 2014
Resumen recomendaciones papps 2014Resumen recomendaciones papps 2014
Resumen recomendaciones papps 2014
 
L'agilité dans la mobilité
L'agilité dans la mobilitéL'agilité dans la mobilité
L'agilité dans la mobilité
 
Cie 9 Avantages Maison
Cie 9 Avantages MaisonCie 9 Avantages Maison
Cie 9 Avantages Maison
 
Aceptacion
AceptacionAceptacion
Aceptacion
 
Revista de computacion
Revista de computacionRevista de computacion
Revista de computacion
 
Chapter6
Chapter6Chapter6
Chapter6
 
Memes
MemesMemes
Memes
 
Kryzalid Agence Web
Kryzalid Agence WebKryzalid Agence Web
Kryzalid Agence Web
 
Alejandro Magno
Alejandro MagnoAlejandro Magno
Alejandro Magno
 
Webassadors - Mixology #4 - Actu' Web de la semaine du 28.07.14
Webassadors - Mixology #4 - Actu' Web de la semaine du 28.07.14Webassadors - Mixology #4 - Actu' Web de la semaine du 28.07.14
Webassadors - Mixology #4 - Actu' Web de la semaine du 28.07.14
 
Dossier de presse BCV (dtp 83)
Dossier de presse BCV (dtp 83)Dossier de presse BCV (dtp 83)
Dossier de presse BCV (dtp 83)
 
Redes sociales
Redes socialesRedes sociales
Redes sociales
 
Una buena reflexion
Una buena reflexionUna buena reflexion
Una buena reflexion
 
Cuales son los detonantes para que se conviertan en hikikomoris
Cuales son los detonantes para que se conviertan en hikikomorisCuales son los detonantes para que se conviertan en hikikomoris
Cuales son los detonantes para que se conviertan en hikikomoris
 

Ähnlich wie Cours algorithmique et complexite complet

la complexité des algorithmes en toute simplicité
la complexité des algorithmes en toute simplicitéla complexité des algorithmes en toute simplicité
la complexité des algorithmes en toute simplicitéSana REFAI
 
Présentation Finale - Partie I.pptx
Présentation Finale - Partie I.pptxPrésentation Finale - Partie I.pptx
Présentation Finale - Partie I.pptxouassityoussef
 
cours algorithme
cours algorithmecours algorithme
cours algorithmemohamednacim
 
1 analyse-et-mesure-des-performances
1 analyse-et-mesure-des-performances1 analyse-et-mesure-des-performances
1 analyse-et-mesure-des-performancesm.a bensaaoud
 
Rapport Projet Module Complexité
Rapport Projet Module ComplexitéRapport Projet Module Complexité
Rapport Projet Module ComplexitéFatima Zahra Fagroud
 
TAD (1).pptx
TAD (1).pptxTAD (1).pptx
TAD (1).pptxSergeOngolo
 
Chapitre i introduction et motivations
Chapitre i introduction et motivationsChapitre i introduction et motivations
Chapitre i introduction et motivationsSana Aroussi
 
Chapitre 3 _Conception et analyse d’algorithme-DPR.pdf
Chapitre 3 _Conception et analyse d’algorithme-DPR.pdfChapitre 3 _Conception et analyse d’algorithme-DPR.pdf
Chapitre 3 _Conception et analyse d’algorithme-DPR.pdfMbarkiIsraa
 
Chap5 La manipulation des iterables en python
Chap5 La manipulation des iterables en pythonChap5 La manipulation des iterables en python
Chap5 La manipulation des iterables en pythonMariem ZAOUALI
 
Cours_3_0910_2.pdf
Cours_3_0910_2.pdfCours_3_0910_2.pdf
Cours_3_0910_2.pdfSongSonfack
 
Cours - TC - Histoire Algorithmique.pdf
Cours - TC - Histoire Algorithmique.pdfCours - TC - Histoire Algorithmique.pdf
Cours - TC - Histoire Algorithmique.pdfadeljaouadi
 
Chapitre 1 rappel
Chapitre 1   rappelChapitre 1   rappel
Chapitre 1 rappelSana Aroussi
 
Mathématiques et Python
Mathématiques et PythonMathématiques et Python
Mathématiques et PythonDany-Jack Mercier
 
Algorithmique seconde (corrigés et commentaires)
Algorithmique seconde (corrigés et commentaires)Algorithmique seconde (corrigés et commentaires)
Algorithmique seconde (corrigés et commentaires)DriNox NordisTe
 
COURS_PYTHON_22.ppt
COURS_PYTHON_22.pptCOURS_PYTHON_22.ppt
COURS_PYTHON_22.pptIbtissameAbbad1
 
Traitement des données massives (INF442, A2)
Traitement des données massives (INF442, A2)Traitement des données massives (INF442, A2)
Traitement des données massives (INF442, A2)Frank Nielsen
 

Ähnlich wie Cours algorithmique et complexite complet (20)

la complexité des algorithmes en toute simplicité
la complexité des algorithmes en toute simplicitéla complexité des algorithmes en toute simplicité
la complexité des algorithmes en toute simplicité
 
Présentation Finale - Partie I.pptx
Présentation Finale - Partie I.pptxPrésentation Finale - Partie I.pptx
Présentation Finale - Partie I.pptx
 
cours algorithme
cours algorithmecours algorithme
cours algorithme
 
1 analyse-et-mesure-des-performances
1 analyse-et-mesure-des-performances1 analyse-et-mesure-des-performances
1 analyse-et-mesure-des-performances
 
Rapport Projet Module Complexité
Rapport Projet Module ComplexitéRapport Projet Module Complexité
Rapport Projet Module Complexité
 
TAD (1).pptx
TAD (1).pptxTAD (1).pptx
TAD (1).pptx
 
Chapitre i introduction et motivations
Chapitre i introduction et motivationsChapitre i introduction et motivations
Chapitre i introduction et motivations
 
langage C++
langage C++langage C++
langage C++
 
Chapitre 3 _Conception et analyse d’algorithme-DPR.pdf
Chapitre 3 _Conception et analyse d’algorithme-DPR.pdfChapitre 3 _Conception et analyse d’algorithme-DPR.pdf
Chapitre 3 _Conception et analyse d’algorithme-DPR.pdf
 
Chap5 La manipulation des iterables en python
Chap5 La manipulation des iterables en pythonChap5 La manipulation des iterables en python
Chap5 La manipulation des iterables en python
 
Cours_3_0910_2.pdf
Cours_3_0910_2.pdfCours_3_0910_2.pdf
Cours_3_0910_2.pdf
 
Cours_3_0910.pdf
Cours_3_0910.pdfCours_3_0910.pdf
Cours_3_0910.pdf
 
algo-imsi-2.pdf
algo-imsi-2.pdfalgo-imsi-2.pdf
algo-imsi-2.pdf
 
Cours - TC - Histoire Algorithmique.pdf
Cours - TC - Histoire Algorithmique.pdfCours - TC - Histoire Algorithmique.pdf
Cours - TC - Histoire Algorithmique.pdf
 
Chapitre 1 rappel
Chapitre 1   rappelChapitre 1   rappel
Chapitre 1 rappel
 
Rapport MOGPL
Rapport MOGPLRapport MOGPL
Rapport MOGPL
 
Mathématiques et Python
Mathématiques et PythonMathématiques et Python
Mathématiques et Python
 
Algorithmique seconde (corrigés et commentaires)
Algorithmique seconde (corrigés et commentaires)Algorithmique seconde (corrigés et commentaires)
Algorithmique seconde (corrigés et commentaires)
 
COURS_PYTHON_22.ppt
COURS_PYTHON_22.pptCOURS_PYTHON_22.ppt
COURS_PYTHON_22.ppt
 
Traitement des données massives (INF442, A2)
Traitement des données massives (INF442, A2)Traitement des données massives (INF442, A2)
Traitement des données massives (INF442, A2)
 

Cours algorithmique et complexite complet

  • 1. Algorithmique et complexitĂ© Mr. Slim Mesfar Mail: mesfarslim@yahoo.fr A.U. 2011-2012
  • 2. Plan du cours  Chap-1: Introduction & motivations  Chap-2: ComplexitĂ© & optimalitĂ©  Chap-3: Algorithmes de tri: analyse et estimation de la complexitĂ©  Chap-4: RĂ©cursivitĂ© ïź DiffĂ©rents types de rĂ©cursivitĂ© ïź DĂ©rĂ©cursivation d’algorithmes ïź RĂ©cursivitĂ© terminale et non terminale ïź Paradigme « diviser pour rĂ©gner »  Chap-5: Graphes et arbres  Chap-6: Arbres binaires de recherche
  • 3. Objectifs du cours  Elaborer des algorithmes performants et efficaces  Comprendre la notion de complexitĂ© d’un algorithme  MaĂźtriser la rĂ©cursivitĂ© (simple, multiple, mutuelle, imbriquĂ©e)  Savoir dĂ©rĂ©cursiver des algorithmes simples et multiples  MaĂźtriser la dĂ©marche « diviser pour rĂ©gner »  Savoir estimer la complexitĂ© d’un algorithme itĂ©ratif ou rĂ©cursif pouvant conduire Ă  des rĂ©currences linĂ©aires d’ordre 1, d’ordre 2 et des rĂ©currences de type « diviser rĂ©gner »  ConnaĂźtre les diffĂ©rents algorithmes de tri et estimer leur complexitĂ©  Elaborer des algorithmes Ă  base de graphes et d’arbres  RĂ©aliser des algorithmes de parcours de graphes et d’arbres
  • 4. Chapitre 1 – Introduction et motivations
  • 5. Introduction Un algorithme = une suite ordonnĂ©e d'opĂ©rations ou d'instruction Ă©crites pour la rĂ©solution d'un problĂšme donnĂ©.  Algorithme = une suite d’actions que devra effectuer un automate pour arriver Ă  partir d’un Ă©tat initial, en un temps fini, Ă  un rĂ©sultat  L’algorithmique dĂ©signe le processus de recherche d’algorithme
  • 6. Structures de donnĂ©es  Une structure de donnĂ©es indique la maniĂšre d'organisation des donnĂ©es dans la mĂ©moire.  Le choix d'une structure de donnĂ©es adĂ©quate dĂ©pend gĂ©nĂ©ralement du problĂšme Ă  rĂ©soudre.  Deux types de structures de donnĂ©es : ïź Statiques : Les donnĂ©es peuvent ĂȘtre manipulĂ©es dans la mĂ©moire dans un espace statique allouĂ© dĂšs le dĂ©but de rĂ©solution du problĂšme. Ex : les tableaux ïź Dynamiques : On peut allouer de la mĂ©moire pour y stocker des donnĂ©es au fur et Ă  mesure des besoins de la rĂ©solution du problĂšme. Ex: liste chainĂ©e, pile, file, 
  notion des pointeurs  nĂ©cessitĂ© de la gestion des liens entre les donnĂ©es d'un problĂšme en mĂ©moire.
  • 7. QualitĂ©s d’un bon algorithme  Correct: Il faut que le programme exĂ©cute correctement les tĂąches pour lesquelles il a Ă©tĂ© conçu  Complet: Il faut que le programme considĂšre tous les cas possibles et donne un rĂ©sultat dans chaque cas.  Efficace: Il faut que le programme exĂ©cute sa tĂąche avec efficacitĂ© c’est Ă  dire avec un coĂ»t minimal. Le coĂ»t pour un ordinateur se mesure en termes de temps de calcul et d’espace mĂ©moire nĂ©cessaire.
  • 8. Exemple : Calcul de la valeur d’un polynĂŽme  Soit P(X) un polynĂŽme de degrĂ© n P(X) = anXn + an-1Xn-1 + ... + a1X + a0  OĂč, ïź n : entier naturel ïź an, an-1, ..., a1, a0 : les coefficients du polynĂŽme  1Ăšre variante : dĂ©but CoĂ»t de l’algorithme : P=0 - (n+1) additions Pour i de 0 Ă  n faire - (n+1) multiplications - (n+1) puissances P = P+ ai*Xi finpour fin
  • 9. Exemple : Calcul de la valeur d’un polynĂŽme  2Ăšme variante : CoĂ»t de l’algorithme : debut - (n+1) additions Inter=1 - 2(n+1) multiplications P =0 Pour i de 0 Ă  N faire P = P+ Inter *ai Inter = Inter * X finpour Fin
  • 10. Exemple : Calcul de la valeur d’un polynĂŽme  3Ăšme variante : SchĂ©ma de Horner P(x) = (
.(((anx+an-1)x+an-2)x+an-3)
..)x+a0 dĂ©but P = an Pour i de n-1 Ă  0 (pas = –1) faire P = P*X + ai CoĂ»t de l’algorithme : finpour - n additions Fin - n multiplications  NĂ©cessitĂ© d’estimer le coĂ»t d’un algorithme avant de l’écrire et l’implĂ©menter
  • 11. Chapitre 2 – ComplexitĂ© et optimalitĂ©
  • 12. DĂ©finitions  la complexitĂ© d'un algorithme est la mesure du nombre d'opĂ©rations fondamentales qu'il effectue sur un jeu de donnĂ©es.  La complexitĂ© est exprimĂ©e comme une fonction de la taille du jeu de donnĂ©es.  La complexitĂ© d'un algorithme est souvent dĂ©terminĂ©e Ă  travers une description mathĂ©matique du comportement de cet algorithme.
  • 13. DĂ©finitions  On note Dn l’ensemble des donnĂ©es de taille n et T(d) le coĂ»t de l’algorithme sur la donnĂ©e d.  On dĂ©finit 3 types de complexitĂ© : ïź ComplexitĂ© au meilleur : C'est le plus petit nombre d'opĂ©rations qu'aura Ă  exĂ©cuter l'algorithme sur un jeu de donnĂ©es de taille fixĂ©e, ici Ă  n. ïź ComplexitĂ© au pire : C'est le plus grand nombre d'opĂ©rations qu'aura Ă  exĂ©cuter l'algorithme sur un jeu de donnĂ©es de taille fixĂ©e, ici Ă  n. ïź ComplexitĂ© en moyenne : C'est la moyenne des complexitĂ©s de l'algorithme sur des jeux de donnĂ©es de taille n.
  • 14. DĂ©finitions  C'est l'analyse pessimiste ou au pire qui est gĂ©nĂ©ralement adoptĂ©e.  En effet, de nombreux algorithmes fonctionnent la plupart du temps dans la situation la plus mauvaise pour eux.  l'analyse au pire des cas donne une limite supĂ©rieure de la performance et elle garantit qu'un algorithme ne fera jamais moins bien que ce qu'on a Ă©tabli.  Un algorithme est dit optimal si sa complexitĂ© est la complexitĂ© minimale parmi les algorithmes de sa classe.  MĂȘme si on s’intĂ©resse quasi-exclusivement Ă  la complexitĂ© en temps des algorithmes. Il est parfois intĂ©ressant de s’intĂ©resser Ă  d’autres ressources, comme la complexitĂ© en espace (taille de l’espace mĂ©moire utilisĂ©), la largeur de bande passante requise, etc.
  • 15. Notations mathĂ©matiques  La notation O est celle qui est le plus communĂ©ment utilisĂ©e pour expliquer formellement les performances d'un algorithme.  Cette notation exprime la limite supĂ©rieure d'une fonction dans un facteur constant.  La notation O reflĂšte la courbe ou l'ordre croissance d'un algorithme.  Les rĂšgles de la notation O sont les suivantes : ïź Les termes constants : O(c) = O(1) ïź Les constantes multiplicatives sont omises : O(cT ) = cO(T) = O(T) ïź L'addition est rĂ©alisĂ©e en prenant le maximum : O(T1) + O(T2) = O(T1 + T2) = max(O(T1);O(T2)) ïź La multiplication reste inchangĂ©e mais est parfois rĂ©Ă©crite d'une façon plus compacte :O(T1)O(T2) = O(T1T2)
  • 16. Exemple  On suppose qu’on dispose d'un algorithme dont le temps d'exĂ©cution est dĂ©crit par la fonction T(n) = 3n2+10n+10. L'utilisation des rĂšgles de la notation O nous permet de simplifier en : O(T(n)) = O(3n2 + 10n + 10) = O(3n2) = O(n2)  Pour n = 10 nous avons : ïź Temps d'exĂ©cution de 3n2 : 3(10)2 / 3(10)2+10(10)+10 = 73,2% ïź Temps d'exĂ©cution de 10n : 10(10) / 3(10)2+10(10)+10 = 24,4% ïź Temps d'exĂ©cution de 10 : 10 / 3(10)2+10(10)+10 = 2,4%  Le poids de 3n2 devient encore plus grand quand n = 100, soit 96,7%  on peut nĂ©gliger les quantitĂ©s 10n et 10. Ceci explique les rĂšgles de la notation O.
  • 17. Classes de complexitĂ©  Les algorithmes usuels peuvent ĂȘtre classĂ©s en un certain nombre de grandes classes de complexitĂ©.  Les complexitĂ©s les plus utilisĂ©es sont : ïź Constante : O(1) AccĂ©der au premier Ă©lĂ©ment d'un ensemble de donnĂ©es ïź Logarithmique : O(logn) Couper un ensemble de donnĂ©es en deux parties Ă©gales, puis couper ces moitiĂ©s en deux parties Ă©gales, etc. ïź LinĂ©aire : O(n) Parcourir un ensemble de donnĂ©es ïź Quasi-linĂ©aire : O(nlogn) Couper rĂ©pĂ©titivement un ensemble de donnĂ©es en deux et combiner les solutions partielles pour calculer la solution gĂ©nĂ©rale ïź Quadratique : O(n2) Parcourir un ensemble de donnĂ©es en utilisant deux boucles imbriquĂ©es ïź Polynomiale : O(nP) Parcourir un ensemble de donnĂ©es en utilisant P boucles imbriquĂ©es ïź Exponentielle : O(2n) GĂ©nĂ©rer tous les sous-ensembles possibles d'un ensemble de donnĂ©es
  • 19. Calcul de la complexitĂ©  1. Cas d'une instruction simple : Ă©criture, lecture, affectation Dans le cas d'uns suite d'instructions simples, on considĂšre la complexitĂ© maximale. La complexitĂ© de cette sĂ©quence vaut max(O(1),O(1))=O(1).
  • 20. Calcul de la complexitĂ©  2. Cas d'un traitement conditionnel  3. Cas d'un traitement itĂ©ratif : Boucle Tant Que
  • 21. Calcul de la complexitĂ©  4. Cas d'un traitement itĂ©ratif : Boucle Pour Pour i de indDeb Ă  indFin faire Traitement Fin Pour indFin ∑ O(T i =indDeb Traitement )
  • 22. Exemples de calcul de la complexitĂ©  Exemple 1 : Tri par insertion ïź Principe : Cette mĂ©thode de tri s'apparente Ă  celle utilisĂ©e pour trier ses cartes dans un jeu : on prend une carte, tab[1], puis la deuxiĂšme, tab[2], que l'on place en fonction de la premiĂšre, ensuite la troisiĂšme tab[3] que l'on insĂšre Ă  sa place en fonction des deux premiĂšres et ainsi de suite. Le principe gĂ©nĂ©ral est donc de considĂ©rer que les (i-1) premiĂšres cartes, tab[1],..., tab[i-1] sont triĂ©es et de placer la ie carte, tab[i], Ă  sa place parmi les (i-1) dĂ©jĂ  triĂ©es, et ce jusqu'Ă  ce que i = N.
  • 23. Exemples de calcul de la complexitĂ©  Exemple 1 : Tri par insertion ProcĂ©dure tri_Insertion (var tab : tableau entier [N]) i, k :entier ; tmp : entier ; Pour i de 2 Ă  N faire tmp ← tab[i]; k ← i; Tant que k > 1 ET tab[k - 1] > tmp faire tab[k] ← tab[k - 1]; k ← k - 1; Fin Tant que tab[k] ← tmp; Fin pour Fin
  • 24. Exemples de calcul de la complexitĂ© Exemple 1 : Tri par insertion  Calcul de la complexitĂ©: ïź la taille du tableau Ă  trier est n. ïź On a deux boucles imbriquĂ©es :  La premiĂšre indique l'Ă©lĂ©ment suivant Ă  insĂ©rer dans la partie triĂ©e du tableau.  Elle effectuera n - 1 itĂ©rations puisque le premier Ă©lĂ©ment est dĂ©jĂ  triĂ©.  Pour chaque Ă©lĂ©ment donnĂ© par la premiĂšre boucle, on fait un parcourt dans la partie triĂ©e pour dĂ©terminer son emplacement.
  • 25. Exemples de calcul de la complexitĂ© Exemple 1 : Tri par insertion  Calcul de la complexitĂ©: ïź Au meilleur des cas : le cas le plus favorable pour cet algorithme est quand le tableau est dĂ©jĂ  triĂ© (de taille n)  O(n) ïź Au pire des cas : Le cas le plus dĂ©favorable pour cet algorithme est quand le tableau est inversement triĂ©  on fera une itĂ©ration pour le 1er Ă©lĂ©ment, deux itĂ©rations pour le 2Ăšme et ainsi de suite pour les autres Ă©lĂ©ments. Soit 1+2+3+4+
+(n-1) = n(n + 1) − n  sa complexitĂ© O(n2) 2
  • 26. Exemples de calcul de la complexitĂ© Exemple 1 : Tri par insertion  Calcul de la complexitĂ©: ïź En moyenne des cas : En moyenne, la moitiĂ© des Ă©lĂ©ments du tableau sont triĂ©s, et sur l’autre moitiĂ© ils sont inversement triĂ©s.  O(n2)
  • 27. Exemples de calcul de la complexitĂ©  Exemple 2 : Recherche dichotomique Fonction RechDicho(Tab :Tableau, borneinf :entier, bornesup :entier, elemcherche :entier) : entier Trouve = false ; Tant que ((non trouve) ET (borneinf<=bornesup)) faire mil = (borneinf+bornesup) DIV 2 ; Si (Tab[mil]=elemcherche) Alors trouve=true ; Sinon Si (elemcherche < Tab[mil]) Alors bornesup = mil-1 ; Sinon borneinf = mil+1 ; Fin Si Fin Si Fin Tant que Si (trouve) Alors Retourner (mil) ; Sinon Retourner (-1) ; Fin Si Fin
  • 28. Exemples de calcul de la complexitĂ©  Exemple 2 : Recherche dichotomique  Cette fonction effectue une recherche dichotomique d'un Ă©lĂ©ment dans un tableau triĂ©. Supposons que le tableau est de taille n une puissance de 2 (n = 2q).  Le pire des cas pour la recherche d'un Ă©lĂ©ment est de continuer les divisions jusqu'Ă  obtenir un tableau de taille 1.  q le nombre d'itĂ©rations nĂ©cessaires pour aboutir Ă  un tableau de taille 1 derniĂšre itĂ©ration  taille tableau = 1  La complexitĂ© = log2(n)
  • 29. Chapitre 3 – Les algorithmes de Tri
  • 30. Tri par sĂ©lection  Principe :  Le principe est que pour classer n valeurs, il faut rechercher la plus petite valeur (resp. la plus grande) et la placer au dĂ©but du tableau (resp. Ă  la fin du tableau), puis la plus petite (resp. plus grande) valeur dans les valeurs restantes et la placer Ă  la deuxiĂšme position (resp. en avant derniĂšre position) et ainsi de suite...
  • 31. Tri par sĂ©lection  Algorithme : i, j: entier ; tmp, small : entier ; t : tableau entier [n] ; DĂ©but Pour i de 1 Ă  n-1 faire small←i; Pour j de i+1 Ă  n faire Si t[j] < t[small] alors small ←j ; Fin si Fin pour tmp←t[small];  T(n) = O(nÂČ) t[small] ←t[i]; t[i] ← tmp; Fin pour Fin
  • 32. Tri par propagation / Ă  bulles  Principe :  Il consiste Ă  parcourir le tableau tab en permutant toute paire d'Ă©lĂ©ments consĂ©cutifs (tab[k],tab[k+1]) non ordonnĂ©s - ce qui est un Ă©change et nĂ©cessite donc encore une variable intermĂ©diaire de type entier. AprĂšs le premier parcours, le plus grand Ă©lĂ©ment se retrouve dans la derniĂšre case du tableau, en tab[N], et il reste donc Ă  appliquer la mĂȘme procĂ©dure sur le tableau composĂ© des Ă©lĂ©ments tab[1], ..., tab[N-1].
  • 33. Tri par propagation / Ă  bulles  Algorithme : ProcĂ©dure tri_Bulle (tab : tableau entier [N] ) i, k :entier ;tmp : entier ; Pour i de N Ă  2 faire Pour k de 1 Ă  i-1 faire Si (tab[k] > tab[k+1]) alors tmp ← tab[k]; tab[k] ← tab[k+1]; tab[k+1] ← tmp; Fin si Fin pour  T(n) = O(nÂČ) Fin pour Fin
  • 34. Chapitre 4 – La rĂ©cursivitĂ©
  • 35. DĂ©finitions  Un algorithme est dit rĂ©cursif s'il est dĂ©fini en fonction de lui-mĂȘme.  La rĂ©cursion est un principe puissant permettant de dĂ©finir une entitĂ© Ă  l'aide d'une partie de celle-ci.  Chaque appel successif travaille sur un ensemble d'entrĂ©es toujours plus affinĂ©e, en se rapprochant de plus en plus de la solution d'un problĂšme.
  • 36. Evolution d’un appel rĂ©cursif  L'exĂ©cution d'un appel rĂ©cursif passe par deux phases, la phase de descente et la phase de la remontĂ©e : ïź Dans la phase de descente, chaque appel rĂ©cursif fait Ă  son tour un appel rĂ©cursif. Cette phase se termine lorsque l'un des appels atteint une condition terminale.  condition pour laquelle la fonction doit retourner une valeur au lieu de faire un autre appel rĂ©cursif. ïź Ensuite, on commence la phase de la remontĂ©e. Cette phase se poursuit jusqu'Ă  ce que l'appel initial soit terminĂ©, ce qui termine le processus rĂ©cursif.
  • 37. Les types de rĂ©cursivitĂ© 1/ La rĂ©cursivitĂ© simple : ïź rĂ©cursivitĂ© simple  la fonction contient un seul appel rĂ©cursif dans son corps. ïź Exemple : la fonction factorielle
  • 38. Les types de rĂ©cursivitĂ© ïź Trace d’exĂ©cution de la fonction factorielle (calcul de la valeur de 4!)
  • 39. Les types de rĂ©cursivitĂ© 2/ La rĂ©cursivitĂ© multiple: ïź rĂ©cursivitĂ© multiple  la fonction contient plus d'un appel rĂ©cursif dans son corps ïź Exemple : le calcul du nombre de combinaisons en se servant de la relation de Pascal :
  • 40. Les types de rĂ©cursivitĂ© 3/ La rĂ©cursivitĂ© mutuelle: ïź Des fonctions sont dites mutuellement rĂ©cursives si elles dĂ©pendent les unes des autres ïź Par exemple la dĂ©finition de la paritĂ© d'un entier peut ĂȘtre Ă©crite de la maniĂšre suivante :
  • 41. Les types de rĂ©cursivitĂ© 4/ La rĂ©cursivitĂ© imbriquĂ©e: ïź Exemple : La fonction d'Ackermann
  • 42. RĂ©cursivitĂ© terminale vs. non terminale  Une fonction rĂ©cursive est dite rĂ©cursive terminale si tous ses appels sont rĂ©cursifs terminaux.  Un appel rĂ©cursif est terminal s'il s'agit de la derniĂšre instruction exĂ©cutĂ©e dans le corps d'une fonction et que sa valeur de retour ne fait pas partie d'une expression.  Les fonctions rĂ©cursives terminales sont caractĂ©risĂ©es par le fait qu'elles n'ont rien Ă  faire pendant la phase de remontĂ©e
  • 43. Importance de l’ordre des appels rĂ©cursifs Proc. terminale Proc. non terminale ProcĂ©dure AfficherGaucheDroite ( ProcĂ©dure AfficherDroiteGauche ( Tab : Tableau entier, N : entier, Tab : Tableau entier, N : entier, i : entier) i : entier) Si (i<=N) Alors Si (i<=N) Alors Ecrire(Tab[i]) ; AfficherDroiteGauche (Tab,N,i+1) ; AfficherGaucheDroite (Tab,N,i+1) ; Ecrire(Tab[i]) ; Fin Si Fin Si Fin Fin  l’ordre des appels rĂ©cursifs affecte la terminaison d’une fonction rĂ©cursive
  • 44. Importance de l’ordre des appels rĂ©cursifs
  • 45. Elimination de la rĂ©cursivitĂ©  DĂ©rĂ©cursiver, c’est transformer un algorithme rĂ©cursif en un algorithme Ă©quivalent ne contenant pas des appels rĂ©cursifs.  Elimination de la rĂ©cursivitĂ© terminale simple ïź Rappel : Un algorithme est dit rĂ©cursif terminal s’il ne contient aucun traitement aprĂšs un appel rĂ©cursif. ïź La rĂ©cursivitĂ© terminale simple peut ĂȘtre remplacĂ©e par une solution itĂ©rative.
  • 46. Elimination de la rĂ©cursivitĂ© terminale simple Algo. rĂ©cursif Algo. itĂ©ratif ProcĂ©dure ALGOR(X) ProcĂ©dure ALGOI(X) Si (COND) Alors Tant que (COND) faire TRAIT1 TRAIT1 ALGOR(ÎČ (X)) X  ÎČ (X) Sinon Fin tant que TRAIT2 TRAIT2 Fin Si Fin Fin ‱X est la liste des paramĂštres ; ‱ COND est une condition portant sur X ; ‱ TRAIT1 est le traitement de base de l'algorithme (dĂ©pendant de X) ; ‱ ÎČ(X) reprĂ©sente la transformation des paramĂštres ; ‱ TRAIT2 est le traitement de terminaison (dĂ©pendant de X).
  • 47. Application : a est diviseur de b ? Algo. rĂ©cursif Algo. itĂ©ratif Fonction Diviseur (a,b) : Bool Fonction Diviseur (a,b) : Bool Si (a <=0) Alors Si (a <=0) Alors Retourner(Faux) Retourner(Faux) Sinon Sinon Si (a>=b) Retourner (a=b) Tant que (a<b) Faire Sinon b  b-a Retourner (Diviseur (a,b-a)) Fin tant que Fin Si Retourner (a=b) Fin Si Fin Si Fin Fin
  • 48. Elimination de la rĂ©cursivitĂ© non terminale simple  Dans un algorithme rĂ©cursif non terminal, l’appel rĂ©cursif est suivi d’un traitement  il reste un traitement Ă  reprendre aprĂšs l’appel rĂ©cursif  Il va falloir donc sauvegarder, sur une pile, le contexte de l’appel rĂ©cursif, typiquement les paramĂštres de l’appel engendrant l’appel rĂ©cursif.  La rĂ©cursivitĂ© non terminale simple peut ĂȘtre remplacĂ©e par une solution itĂ©rative utilisant une pile.
  • 49. Elimination de la rĂ©cursivitĂ© non terminale simple Algo. rĂ©cursif Algo. itĂ©ratif ProcĂ©dure ALGOR(X) ProcĂ©dure ALGOI(X) Si (COND) Alors Pile.init() TRAIT1 Tant que (COND) Faire ALGOR(ÎČ (X)) TRAIT1 TRAIT2 Pile.empiler(X) Sinon X  ÎČ (X) TRAIT3 Fin Tant que Fin Si TRAIT3 Fin Tant que (Non_vide_pile()) Faire Pile.dĂ©piler(U) TRAIT2 Fin Tant que Fin
  • 50. Elimination de la rĂ©cursivitĂ© non terminale simple Algo. rĂ©cursif Algo. itĂ©ratif ProcĂ©dure ProcĂ©dure ALGOI(X) AfficherDroiteGauche ( Tab Pile.init() : Tableau entier, N : Tant que (i<=N) Faire entier, i : entier) /* TRAIT1 */ Si (i<=N) Alors Pile.empiler(Tab[i]) AfficherDroiteGauche i  i+1 (Tab,N,i+1) ; Ecrire(Tab[i]) ; Fin Tant que Fin Si /* TRAIT3 */ Fin Tant que (Non_vide_pile()) Faire TRAIT1 = Ø Ecrire(Pile.dĂ©piler() ) TRAIT2 = Ecrire(Tab[i]) /* TRAIT2 */ TRAIT3 = Ø Fin Tant que Fin
  • 51. Exemple : Tours de Hanoi  ProblĂšme : Le jeu est constituĂ© d’une plaquette de bois oĂč sont plantĂ©es trois tiges numĂ©rotĂ©es 1, 2 et 3. Sur ces tiges sont empilĂ©s des disques de diamĂštres tous diffĂ©rents. Les seules rĂšgles du jeu sont que l’on ne peut dĂ©placer qu’un seul disque Ă  la fois, et qu’il est interdit de poser un disque sur un disque plus petit. Au dĂ©but, tous les disques sont sur la tige 1 (celle de gauche), et Ă  la fin ils doivent ĂȘtre sur celle de droite.
  • 52. Exemple : Tours de Hanoi  RĂ©solution:  On suppose que l’on sait rĂ©soudre le problĂšme pour (n-1) disques. Pour dĂ©placer n disques de la tige 1 vers la tige 3, on dĂ©place les (n-1) plus petits disques de la tige 1 vers la tige 2, puis on dĂ©place le plus gros disque de la tige 1 vers la tige 3, puis on dĂ©place les (n-1) plus petits disques de la tige 2 vers la tige 3.
  • 53. Exemple : Tours de Hanoi  Algorithme ProcĂ©dure Hanoi (n, dĂ©part, intermĂ©diaire, destination) Si n > 0 Alors Hanoi (n-1, dĂ©part, destination, intermĂ©diaire) dĂ©placer un disque de dĂ©part vers destination Hanoi (n-1, intermĂ©diaire, dĂ©part, destination) Fin Si Fin
  • 54. Exemple : Tours de Hanoi  Trace d’exĂ©cution pour n=3 L’appel Ă  Hanoi(3,1,2,3) entraĂźne l’affichage de : 1. DĂ©place un disque de la tige 1 vers la tige 3 2. DĂ©place un disque de la tige 1 vers la tige 2 3. DĂ©place un disque de la tige 3 vers la tige 2 4. DĂ©place un disque de la tige 1 vers la tige 3 5. DĂ©place un disque de la tige 2 vers la tige 1 6. DĂ©place un disque de la tige 2 vers la tige 3 7. DĂ©place un disque de la tige 1 vers la tige 3
  • 55. Exemple : Tours de Hanoi  Calcul de la complexitĂ© :  On compte le nombre de dĂ©placements de disques effectuĂ©s par l’algorithme Hanoi invoquĂ© sur n disques.  On trouve : ïź T(n) = T(n-1) + 1 + T(n-1) ïź T(n) = 2T(n-1) + 1  T(n) = 2n – 1  ComplexitĂ© exponentielle
  • 56. Paradigme « diviser pour rĂ©gner »  De nombreux algorithmes ont une structure rĂ©cursive: pour rĂ©soudre un problĂšme donnĂ©, ils s’appellent eux-mĂȘmes rĂ©cursivement une ou plusieurs fois sur des problĂšmes trĂšs similaires, mais de tailles moindres, rĂ©solvent les sous problĂšmes de maniĂšre rĂ©cursive puis combinent les rĂ©sultats pour trouver une solution au problĂšme initial.  Le paradigme « diviser pour rĂ©gner » parcourt trois Ă©tapes Ă  chaque appel rĂ©cursif Ă  savoir : ïź Diviser : le problĂšme en un certain nombre de sous- problĂšmes de taille moindre ; ïź RĂ©gner : sur les sous-problĂšmes en les rĂ©solvant d'une façon rĂ©cursive ou le rĂ©soudre directement si la taille d'un sous- problĂšme est assez rĂ©duite ; ïź Combiner : les solutions des sous-problĂšmes en une solution globale pour le problĂšme initial.
  • 57. Exemple 1  Recherche de l’indice du maximum dans un tableau d’entiers Fonction maximum ( Tab , indDeb, indFin) Si ( indDeb = indFin) alors retourner (indDeb) Sinon m=(indDeb+indFin)/2 // division du problĂšme en 2 sous-problĂšmes k1 = maximum (Tab, indDeb, m ) // rĂ©gner sur le 1er sous-problĂšme k2 = maximum (Tab, m+1, indFin)// rĂ©gner sur le 2Ăšme sous-problĂšme Si(Tab[k1] > Tab[k2]) Alors // combiner les solutions retourner (k1) Sinon retourner (k2)  T(n) = 2 T(n/2) + cte FinSi FinSi Fin
  • 58. Exemple2 : multiplication de matrices carrĂ©es  Dans cet exemple, on se propose de multiplier 2 matrices carrĂ©es A et B de taille n * n chacune, oĂč n est une puissance exacte de 2. C est la matrice rĂ©sultante.  Si on dĂ©compose les matrices A, B et C en sous- matrices de taille n/2 * n/2, l'Ă©quation C = AB peut alors se rĂ©Ă©crire :  Le dĂ©veloppement de cette Ă©quation donne : r = ae+bf ; s = ag+bh; t = ce+df et u = cg+dh
  • 59. Exemple2 : multiplication de matrices carrĂ©es  Chacune de ces quatre opĂ©rations correspond Ă  : ïź deux multiplications de matrices carrĂ©es de taille n/2  2T(n/2) ïź et une addition de telles matrices n2/4  A partir de ces Ă©quations on peut dĂ©river un algorithme « diviser pour rĂ©gner » dont la complexitĂ© est donnĂ©e par la rĂ©currence :  T(n) = 8T(n/2)+O(n2)
  • 60. Analyse des algorithmes « Diviser pour RĂ©gner »  On peut souvent donner une relation de rĂ©currence qui dĂ©crit le temps d'exĂ©cution d’un algorithme « diviser pour rĂ©gner » en fonction des temps d'exĂ©cution des appels rĂ©cursifs rĂ©solvant les sous-problĂšmes associĂ©s de taille moindre.  Cette rĂ©currence se dĂ©compose suivant les trois Ă©tapes du paradigme de base : ïź Si la taille du problĂšme est suffisamment rĂ©duite, n ≀ c pour une certaine constante c, la rĂ©solution est directe et consomme un temps constant O(1). ïź Sinon, on divise le problĂšme en a sous-problĂšmes chacun de taille 1/b de la taille du problĂšme initial. Le temps d'exĂ©cution total se dĂ©compose alors en trois parties :  D(n) : le temps nĂ©cessaire Ă  la division du problĂšme en sous- problĂšmes.  aT (n/b) : le temps de rĂ©solution des a sous-problĂšmes.  C(n) : le temps nĂ©cessaire pour construire la solution finale Ă  partir des solutions aux sous-problĂšmes.
  • 61. Analyse des algorithmes « Diviser pour RĂ©gner »  La relation de rĂ©currence prend alors la forme :  Soit la fonction f (n) la fonction qui regroupe D(n) et C(n). La fonction T(n) est alors dĂ©finie : T(n) = a.T(n / b) + f (n) T (n) = a.T (n / b) + c.nk
  • 62. RĂ©solution des rĂ©currence des algorithmes « Diviser pour RĂ©gner »  ThĂ©orĂšme de rĂ©solution de la rĂ©currence : ïź si a > bk  T(n) = O(nlogb a ) ïź si a = bk  T(n) = O(nk logbn) ïź si a < bk  T(n) = O( f (n)) = O(nk )  RĂ©solution de la relation de rĂ©currence pour l’exemple de la multiplication de matrices : ïź T(n) = 8 T(n/2) + O(n2) ïź a = 8 , b = 2, k = 2  a > bk  Logba = 3  T(n) = O(n3)
  • 63. Analyse des algorithmes « Diviser pour RĂ©gner »  ComplexitĂ© de l’algorithme de recherche du maximum: T(n) = 2 T(n/2) + 3 ïź a = 2 , b = 2, k = 0  a > bk  Logba = 1  T(n) = O(n)
  • 64. Application : algorithme de recherche dichotomique Fonction RechDicho(Tab :Tableau, borneinf :entier, bornesup :entier, elem :entier) : bool Si (borneinf<=bornesup) alors mil = (borneinf+bornesup) DIV 2 ; Si (Tab[mil]=elem) Alors retourner (vrai) Sinon Si (Tab[mil]>elem) Alors Retourner (RechDicho(Tab, borneinf, mil-1, elem)) Sinon Retourner(RechDicho(Tab, mil+1, bornesup, elem)) Fin Si Fin Si Sinon Retourner (Faux) FinSi
  • 65. Application : algorithme de recherche dichotomique  Analyse de la complexitĂ© : ïź T(n) = T(n/2) + cte ïź a = 1 , b = 2, k = 0  a = bk  a = bk  T(n) = O(nk logbn)  T(n) = O(log2n)
  • 66. Exemples d’application ïŁ«nïŁ¶  Exemple 1 : T (n) = 9T ïŁŹ ïŁ· + n ïź a = 9 , b = 3 , k = 1 ïŁ­3ïŁž  a > bk  Logba = 2  T(n) = O(nÂČ) ïŁ« 2n ïŁ¶  Exemple 2 : T ( n) = T ïŁŹ ïŁ· + 1 ïŁ­ 3 ïŁž ïź a = 1 , b = 3/2 , k = 0  a = bk  T(n) = O(nklogn) = O(logn)
  • 67. Exemples d’application ïŁ«nïŁ¶  Exemple 3 : T (n) = 3T ïŁŹ ïŁ· + n log n ïź a = 3 , b = 4 , k = ?? ïŁ­4ïŁž or n < nlogn < nÂČ ïƒš1 < k < 2  4 < bk < 16  a < bk  T(n) = O(f(n)) = O(n logn)
  • 68. Autres rĂ©solutions de rĂ©currence  Equations de rĂ©currence linĂ©aires: ïŁ« n f (i ) ïŁ¶ T (n) = aT (n − 1) + f (n ) T ( n ) = a ïŁŹ T ( 0) + ∑ i ïŁ· n ïŁ­ i =1 a ïŁž  Exemple : Les Tours de Hanoi ïŁ« n 1ïŁ¶  T(n) = 2 T(n-1) + 1  T ( n) = 2 ïŁŹ 0 + ∑ i ïŁ· = 2 − 1 n n ïŁ­ i =1 2 ïŁž
  • 69. Autres rĂ©solutions de rĂ©currence  Equations de rĂ©currence linĂ©aires sans second membre (f(n) = cte) T (n) − a1T (n − 1) − a2T (n − 2 ) − ... − ak T (n − k ) = cte  A une telle Ă©quation, on peut associer un polynĂŽme: P ( x) = x k − a x k −1 − a x k − 2 − ... − a 1 2 k  La rĂ©solution de ce polynĂŽme nous donne m racines ri ( avec m<=k).  La solution de l’équation de rĂ©currence est ainsi donnĂ©e par : T (n) = c1r1 + c2 r2 + c3 r3 + ... + c r n n n n m m  Cette solution est en gĂ©nĂ©ral exponentielle
  • 70. Autres rĂ©solutions de rĂ©currence  Exemple : La suite de Fibonacci  T(n) = T(n-1) + T(n-2)  On pose P(x) = XÂČ - X – 1  r = 1 + 5 et r = 1 − 5 1 2 2 2 ïŁ« 1 + 5 ïŁ¶n ïŁ«1− 5 ïŁ¶ n T (n) = a r1n + b r2n = a ïŁŹ ïŁ· ïŁŹ 2 ïŁ· +b ïŁŹ ïŁŹ 2 ïŁ· ïŁ·  ïŁ­ ïŁž ïŁ­ ïŁž ïŁ« ïŁ« 1 + 5 ïŁ¶n ïŁ¶  T (n) = ÎŸïŁŹ ïŁŹ ïŁ· ïŁ· ïŁŹïŁŹ 2 ïŁ· ïŁ· ïŁ­ïŁ­ ïŁž ïŁž
  • 71. Suite du chapitre 3 – Les algorithmes de Tri
  • 72. Tri par fusion  Principe :  Le principe du tri par fusion est plutĂŽt simple. On dit que trier un tableau de taille N, c'est trier deux tableaux de taille N/2; une fois les deux tableaux triĂ©s on n’a plus qu'Ă  les rĂ©unir (les fusionner) de sorte Ă  ce que le tableau final soit triĂ©. Ce tri bien sĂ»r utilise une notion de rĂ©cursivitĂ© (un tableau Ă©tant la somme de deux tableaux).
  • 73. Tri par fusion  Algorithme : Fonction tri_fusion (T, deb, fin) : tableau entier T1, T2 : tableau entier [N/2] ; Si (deb >= fin) alors Retourner T ; Sinon mil = (deb + fin) DIV 2; T1 = tri_fusion (T, deb, mil) ; T2 = tri_fusion (T, mil+1, fin)) ; Retourner fusion (T1, T2) ; Fin si FIN  T(n) = 2 T(n/2) + Tfusion(n)
  • 74. Tri par fusion Fonction fusion (T1, T2) : tableau entier T1 : tableau entier [1...N] ; T2 : tableau entier [1...M] ; T: tableau entier [1...M+N] ; i, j: entier; i←1 ;j←1 ; Tantque (i+j-1 <> N+M) faire Si (i ≀ N) alors si (j ≀ M) alors si (T1[i] < T2[j]) alors T[i+j-1]←T1[i] ; i←i+1 ; sinon T[i+j-1]←T2[j] ; j←j+1 ; Fin si sinon T[i+j-1]←T1[i]; i←i+1; Fin si sinon T[i+j-1]←T2[j] ; j←j+1 ; Fin si FinTanque Retourner T ;FIN  Tfusion(n) = O(n)
  • 75. Tri par fusion L’algorithme Tri_Fusion est de type « diviser pour rĂ©gner ». Il faut donc Ă©tudier ses trois phases:  Diviser : cette Ă©tape se rĂ©duit au calcul du milieu de l’intervalle [deb,fin], sa complexitĂ© est donc en O(1).  RĂ©gner : l’algorithme rĂ©sout rĂ©cursivement deux sous-problĂšmes de tailles respectives (n/2) , d’oĂč une complexitĂ© en 2T(n/2).  Combiner : la complexitĂ© de cette Ă©tape est celle de l’algorithme de fusion qui est de O(n) pour la construction d’un tableau solution de taille n.
  • 76. Tri par fusion  T(n) = 2 T(n/2) + O(n)  Rappel : ThĂ©orĂšme de rĂ©solution de la rĂ©currence T(n) = a T(n/b) + O(nk): ïź si a > bk  T(n) = O(nlogb a ) ïź si a = bk  T(n) = O(nk logbn) ïź si a < bk  T(n) = O( f (n)) = O(nk ) a = 2, b = 2, k = 1 (2Ăšme cas)  T(n) = O(n log2n)
  • 77. Tri rapide (Quicksort)  Principe : Le tri rapide est fondĂ© sur le paradigme « diviser pour rĂ©gner», tout comme le tri par fusion, il se dĂ©compose donc en trois Ă©tapes :  Diviser : Le tableau T[deb..fin] est partitionnĂ© (et rĂ©arrangĂ©) en deux sous-tableaux non vides, T[deb..inter] et T[inter+1..fin] tels que chaque Ă©lĂ©ment de T[deb..fin] soit infĂ©rieur ou Ă©gal Ă  chaque Ă©lĂ©ment de T[inter+1..fin]. L’indice inter est calculĂ© pendant la procĂ©dure de partitionnement.  RĂ©gner : Les deux sous-tableaux T[deb..inter] et T[inter+1..fin] sont triĂ©s par des appels rĂ©cursifs.  Combiner : Comme les sous-tableaux sont triĂ©s sur place, aucun travail n’est nĂ©cessaire pour les recombiner, le tableau T[deb..fin] est dĂ©jĂ  triĂ© !
  • 78. Tri rapide Tri_Rapide (T, deb, fin) Si (deb < fin ) alors inter =Partionner (T, deb, fin) Tri_Rapide (T, deb, inter) Tri_Rapide (T, inter+1, fin) Fin si Partionner (T, deb, fin) x = T(deb) i = deb-1 ; j= fin+1 Tant que (1) RĂ©pĂ©ter { j=j-1 } Jusqu’à T(j) <= x RĂ©pĂ©ter { i =i+1 } Jusqu’à T(i) >= x si ( i < j ) permuter (T(i), T(j)) sinon retourner j Fin Si Fin
  • 79. Tri rapide : calcul de la complexitĂ©  Pire cas Le cas pire intervient quand le partitionnement produit une rĂ©gion Ă  n-1 Ă©lĂ©ments et une Ă  1 Ă©lĂ©ment. Comme le partitionnement coĂ»te O(n) et que T(1) = O(1), la rĂ©currence pour le temps d’exĂ©cution est : T(n) = T(n-1) +O(n) et par sommation on obtient : T(n) = O(nÂČ)  Meilleur cas : Le meilleur cas intervient quand le partitionnement produit deux rĂ©gions de longueur n/2. La rĂ©currence est alors dĂ©finie par : T(n) = 2T(n / 2) + O(n) ce qui donne d’aprĂšs le thĂ©orĂšme de rĂ©solution des rĂ©currences : T(n) = O(nlog n)
  • 81. Les graphes  Un graphe orientĂ© G est reprĂ©sentĂ© par un couple (S, A) oĂč S est un ensemble fini et A une relation binaire sur S. L’ensemble S est l’ensemble des sommets de G et A est l’ensemble des arcs de G.  Il existe deux types de graphes : ïź graphe orientĂ© : les relations sont orientĂ©es et on parle d’arc. Un arc est reprĂ©sentĂ© par un couple de sommets ordonnĂ©s. ïź Graphe non orientĂ© : les relations ne sont pas orientĂ©es et on parle alors d’arĂȘtes. Une arĂȘte est reprĂ©sentĂ©e par une paire de sommets non ordonnĂ©s.
  • 82. Les graphes  Une boucle est un arc qui relie un sommet Ă  lui-mĂȘme. Dans un graphe non orientĂ© les boucles sont interdites et chaque arĂȘte est donc constituĂ©e de deux sommets distincts.  DegrĂ© d’un sommet : Dans un graphe non orientĂ©, le degrĂ© d’un sommet est le nombre d’arĂȘtes qui lui sont incidentes. Si un sommet est de degrĂ© 0, il est dit isolĂ©.  DegrĂ© sortant d’un sommet : Dans un graphe orientĂ©, le degrĂ© sortant d’un sommet est le nombre d’arcs qui en partent,  DegrĂ© rentrant d’un sommet : le degrĂ© entrant est le nombre d’arcs qui y arrivent et le degrĂ© est la somme du degrĂ© entrant et du degrĂ© sortant.  Chemin : Dans un graphe orientĂ© G = (S,A), un chemin de longueur k d’un sommet u Ă  un sommet v est une sĂ©quence (u0,u1,
, uk) de sommets telle que u = u0, v = uk et (ui-1, ui) appartient Ă  A pour tout i. Un chemin est Ă©lĂ©mentaire si ses sommets sont tous distincts
  • 83. Les graphes  Un sous-chemin p0 d’un chemin p = (u0,u1, 
. ,uk) est une sous- sĂ©quence contiguĂ« de ses sommets. Autrement dit, il existe i et j, 0<=i<= j <=k, tels que p0 = (ui,ui+1, 
. ,uj).  Circuit : Dans un graphe orientĂ© G=(S,A), un chemin (u0,u1, 
. ,uk) forme un circuit si u0 =uk et si le chemin contient au moins un arc. Ce circuit est Ă©lĂ©mentaire si les sommets u0, ..., uk sont distincts. Une boucle est un circuit de longueur 1.  Cycle : Dans un graphe non orientĂ© G = (S,A), une chaĂźne (u0,u1,
., uk) forme un cycle si k >= 2 et si u0 = uk. Ce cycle est Ă©lĂ©mentaire si les sommets u0, ..., uk sont distincts. Un graphe sans cycle est dit acyclique.  Sous-graphe : On dit qu’un graphe G0 = (S0,A0) est un sous- graphe de G = (S,A) si S0 est inclus dans S et si A0 est inclus dans A.
  • 84. Les arbres  PropriĂ©tĂ©s des arbres : Soit G = (S,A) un graphe non orientĂ©. Les affirmations suivantes sont Ă©quivalentes. ïź 1. G est un arbre. ïź 2. Deux sommets quelconques de G sont reliĂ©s par un unique chemin Ă©lĂ©mentaire. ïź 3. G est acyclique et |A| = |S| - 1 ïź 4. G est acyclique, mais si une arĂȘte quelconque est ajoutĂ©e Ă  A, le graphe rĂ©sultant contient un cycle.
  • 85. Arbres – dĂ©finitions  Arbre enracinĂ© (ou arborescence): C’est un arbre dans lequel l’un des sommets se distingue des autres. On appelle ce sommet la racine. Ce sommet particulier impose en rĂ©alitĂ© un sens de parcours de l’arbre  AncĂȘtre : Soit x un noeud (ou sommet) d’un arbre A de racine r. Un noeud quelconque y sur l’unique chemin allant de r Ă  x est appelĂ© ancĂȘtre de x.  PĂšre et fils : Si (y,x) est un arc alors y est le pĂšre de x et x est le fils de y. La racine est le seul noeud qui n’a pas de pĂšre.  Feuille ou noeud externe (ou terminal) : Une feuille est un noeud sans fils. Un noeud qui n’est pas une feuille est un noeud interne.  Sous-arbre : Le sous-arbre de racine x est l’arbre composĂ© des descendants de x, enracinĂ© en x.
  • 86. Arbres - dĂ©finitions  DegrĂ© d’un nƓud : Le nombre de fils du nƓud x est appelĂ© le degrĂ© de x.  Profondeur d’un nƓud : La longueur du chemin entre la racine r et le nƓud x est la profondeur de x.  Profondeur de l’arbre : c’est la plus grande profondeur que peut avoir un nƓud quelconque de l’arbre. Elle est dite aussi la hauteur de l’arbre.  Arbre binaire : c’est un arbre dont chaque nƓud a au plus deux fils.  Arbre binaire complet : Dans un arbre binaire complet chaque nƓud est soit une feuille, soit de degrĂ© deux. Aucun nƓud n’est donc de degrĂ© 1.
  • 87. Parcours des arbres  Parcours en profondeur  Dans un parcours en profondeur, on descend d’abord le plus profondĂ©ment possible dans l’arbre puis, une fois qu’une feuille a Ă©tĂ© atteinte, on remonte pour explorer les autres branches en commençant par la branche « la plus basse » parmi celles non encore parcourues. Les fils d’un nƓud sont bien Ă©videmment parcourus suivant l’ordre sur l’arbre.  Algorithme: Algorithme ParPro(A) si A n’est pas rĂ©duit Ă  une feuille alors Pour tous les fils u de racine(A) Faire ParPro(u) Fin pour finSi Fin
  • 88. Parcours des arbres  Parcours en largeur  Dans un parcours en largeur, tous les nƓuds Ă  une profondeur i doivent avoir Ă©tĂ© visitĂ©s avant que le premier nƓud Ă  la profondeur i+1 ne soit visitĂ©. Un tel parcours nĂ©cessite l’utilisation d’une file d’attente pour se souvenir des branches qui restent Ă  visiter.  Algorithme: Algorithme Parcours_Largeur(A) F : File d’attente F.enfiler(racine(A)) Tant que F != vide Faire u=F.dĂ©filer() Afficher (u) Pour « chaque fils v de » u Faire F.enfiler (v) FinPour Fin Tant que Fin
  • 89. Parcours des graphes  Le parcours des graphes est un peu plus compliquĂ© que celui des arbres. En effet, les graphes peuvent contenir des cycles et il faut Ă©viter de parcourir indĂ©finiment ces cycles. Pour cela, il suffit de colorier les sommets du graphe. ïź Initialement les sommets sont tous blancs, ïź lorsqu’un sommet est rencontrĂ© pour la premiĂšre fois il est peint en gris, ïź lorsque tous ses successeurs dans l’ordre de parcours ont Ă©tĂ© visitĂ©s, il est repeint en noir.
  • 90. Parcours des graphes Algorithme Pacours_Profondeur (G) Algorithme VisiterPP(G, s) Pour chaque sommet u de G Faire couleur[s]=Gris couleur[u]=Blanc Pour chaque voisin v de s Faire FinPour Si couleur[v] = Blanc alors Pour chaque sommet u de G Faire VisiterPP(G, v) si couleur[u] = Blanc alors FinSi VisiterPP(G, u) FinPour FinSi couleur[s]=Noir FinPour Fin Fin
  • 91. Parcours des graphes Algorithme Parcours_Largeur(G, s) F : File d’attente Pour chaque sommet u de G Faire couleur[u] = Blanc FinPour couleur[s]=Gris F.enfiler(s) Tant que F != Vide Faire u=F.dĂ©filer() Pour chaque voisin v de u Faire Si couleur(v) = Blanc alors couleur(v)= Gris F.enfiler(v) FinPour Couleur(u)= Noir FinTant que
  • 92. Chapitre 6 – Arbres binaires de recherche
  • 93. DĂ©finitions  Un arbre binaire est un graphe qui admet une racine et sans cycle et dont chaque nƓud admet deux fils : fils droit et fils gauche.  Structure de donnĂ©es : Enregistrement NƓud { Info : Type (entier, rĂ©el, chaine, 
) FilsG : ^ NƓud FilsD : ^ NƓud } Racine : ^NƓud  Il existe 3 mĂ©thodes de parcours d’un arbre binaire : ïź parcours prĂ©fixe : pĂšre, fils gauche, fils droit ïź parcours infixe : fils gauche, pĂšre, fils droit ïź parcours postfixe : fils gauche, fils droit, pĂšre
  • 94. Parcours prĂ©fixĂ© Algorithme PrĂ©fixe(racine : ^NƓud) Si (racine != Nil) Alors AfficheRacine(racine) PrĂ©fixe (racine^.FilsG) PrĂ©fixe (racine^.FilsD) FinSi Fin
  • 95. Parcours prĂ©fixĂ© utilisant une pile  Le programme suivant est une version dĂ©rĂ©cursivĂ©e utilisant une pile explicite et permettant le parcours prĂ©fixĂ© d’un arbre binaire. Algorithme PrĂ©fixe (racine : ^NƓud) P : pile Empiler (P, racine) Tant que (Non_Vide(P)) racine = depiler (P) Empiler (P,racine^.FilsD) Empiler (P,racine^.FilsG) Fin Tant que Fin
  • 96. Parcours infixĂ© Algorithme infixe(racine : ^NƓud) Si (racine != Nil) Alors infixe (racine^.FilsG) AfficheRacine(racine) infixe (racine^.FilsD) FinSi Fin
  • 97. Parcours postfixĂ© Algorithme Postfixe(racine : ^NƓud) Si (racine != Nil) Alors Postfixe (racine^.FilsG) Postfixe (racine^.FilsD) AfficheRacine(racine) FinSi Fin
  • 98. Arbre binaire de recherche  Un arbre binaire de recherche est un arbre binaire dans lequel chaque nƓud est supĂ©rieur Ă  son fils gauche et infĂ©rieur Ă  son fils droit et il n’y a pas de nƓuds Ă©gaux.  Un arbre binaire de recherche est intĂ©ressant puisqu’il est toujours possible de connaĂźtre dans quelle branche de l’arbre se trouve un Ă©lĂ©ment et de proche en proche le localiser dans l’arbre. On peut aussi utiliser un arbre binaire de recherche pour ordonner une liste d’élĂ©ments.
  • 99. Recherche dans un arbre binaire de recherche Algorithme Chercher (racine : ^NƓud , X : Ă©lĂ©ment) Si ( racine = Nil) alors retourner 0 Sinon Si( racine^.info = X ) alors retourner 1 Else Si (X < racine^.info ) alors retourner Chercher(racine^.FilsG, X) Else retourner Chercher (racine^.FilsD, X) Finsi FinSi FinSi Fin
  • 100. Insertion dans un arbre binaire de recherche  L’élĂ©ment Ă  ajouter est insĂ©rĂ© lĂ  oĂč on l’aurait trouvĂ© s’il avait Ă©tĂ© prĂ©sent dans l’arbre. L’algorithme d’insertion recherche donc l’élĂ©ment dans l’arbre et, quand il aboutit Ă  la conclusion que l’élĂ©ment n’appartient pas Ă  l’arbre (il aboutit Ă  la terre), il insĂšre l’élĂ©ment comme fils du dernier nƓud visitĂ©. Algorithme InsĂ©rer (racine : ^NƓud, X : Ă©lĂ©ment ) Si (racine = nil) alors « ajouter un nƓud pour X Ă  cet endroit» Sinon Si (racine^.info = X) Ecrire ("l’élĂ©ment Ă  insĂ©rer existe dĂ©jĂ  dans l’arbre") Sinon Si (X> racine^.info) InsĂ©rer (racine^.FD, X) Sinon InsĂ©rer (racine^.FG, X) Fin
  • 101. Suppression dans un arbre binaire de recherche  1er cas : l’élĂ©ment Ă  supprimer n’a pas de fils  il est terminal et il suffit de le supprimer
  • 102. Suppression dans un arbre binaire de recherche  2Ăšme cas : l’élĂ©ment a un fils unique  on supprime le nƓud et on relie son fils Ă  son pĂšre
  • 103. Suppression dans un arbre binaire de recherche  3Ăšme cas : l’élĂ©ment Ă  supprimer a deux fils  on le remplace par son successeur qui est toujours le minimum de ses descendants droits.
  • 104. Merci pour votre attention !