Vous êtes sur la page 1sur 9

Algorithmique et Programmation 3

STPI - 2A
2021-2022

Moncef Hidane, Pascal Berthomé, Hugot Raguet

Séance 2: Analyser des algorithmes

1 / 18

Comparer des algorithmes

Position du problème
• Souvent, un problème et plusieurs solutions
• Laquelle choisir ?
• Quel(s) critère(s) d’optimalité ?

Ressources
• temps de calcul
• mémoire
• bande passante
• énergie
• ...

2 / 18
Taille des instances
Lien entre taille et temps de calcul
• Le temps de calcul d’un algorithme dépend, généralement, de la taille
des instances : plus la taille est grande plus le temps de calcul est
important.
• Exemple : le temps de calcul nécessaire à un algorithme de tri
particulier augmentera avec la taille de la séquence à trier.
• Dans certains cas très particuliers, le temps de calcul est indépendant
de la taille des instances (par exemple l’accès aux éléments d’un
tableau).

Mesurer la taille
• Première idée : nombre de bits associés aux instances
Type Nombre de bits • Multiplication de 2 entiers :
Caractères 8 (ou 16) 2 × 32 = 64 bits
Entiers 32 (ou 64) • Tri d’un tableau de 100 réels :
Réels 64 100 × 64 = 6400 bits
3 / 18
• Deuxième idée : compter le nombre d’éléments (sans distinguer les
types).
• Multiplication de 2 entiers : 2 éléments
• Tri d’un tableau de 100 réels : 100 éléments

Approche empirique VS approche théorique


Approche empirique
• Programmer et noter les temps de calcul
• Inconvénients : c’est long (développer, débugger, . . . ) et non
généralisable (si on change de machine, de compilateur, d’options de
compilation ?)

Approche théorique
• Se baser sur un modèle
• Modèle : abstraction qui permet de prendre en compte les principales
caractéristiques des plates-formes (matériel et logiciel) qu’on considère

Modèle très simplifié de machine séquentielle


• Les instructions sont exécutées les unes après les autres (pas de
parallélisation)
• Les accès mémoire (lecture et écriture), les opérations arithmétiques
et les tests se font en temps constant, c.à.d. indépendamment du 4 / 18
nombre de bits.
Principe d’invariance
Supposons que l’on mette en œuvre l’algorithme du tri par insertion sur 2
machines différentes M1 et M2 . Notons, pour i ∈ {1, 2}
• ci : coût associé à une opération élémentaire sur la machine i
• Ci : coût associé au tri par insertion sur la machine i.
Il existe une constante a > 0 (indépendante de n) telle que

C1 (n) = a C2 (n).

Principe d’invariance
Deux mises en œuvre d’un même algorithme ne diffèrent que d’une
constante multiplicative.

Conséquence
Pour effectuer une analyse indépendante du matériel, on ne comptera à
présent que le nombre d’opérations élémentaires.
5 / 18

Analyser dans le modèle séquentiel


Compter les opérations
• Analyser = compter le nombre d’opérations élémentaires, en fonction
de la taille des instances.
• Parfois, les temps de calcul associés à 2 instances de même taille
diffèrent.
• C’est le cas par exemple pour le tri (1 séquence triée et une autre triée
dans l’ordre inverse).

Meilleur, pire, moyen


• Analyse dans le meilleur cas : compter le nombre d’opérations dans le
cas le plus favorable.
• tableau déjà trié pour le problème du tri ? L’item recherché est le
premier visité pour le problème de la recherche.
• Analyse dans le pire des cas : compter le nombre d’opérations dans le
cas le plus défavorable.
• tableau trié dans l’ordre inverse pour le problème du tri ? L’item
recherché n’existe pas pour le problème de la recherche. 6 / 18

• Analyse en moyenne : compter le nombre d’opérations dans le cas


Tri par insertion
Fonction tri-insertion(In-Out Variable tab : Tableau d’entiers) : Vide
Variables i, j, clé : Entiers
Pour j allant de 2 à taille(tab) par pas de 1
clé ← tab[j]
// Insère clé dans la séquence tab[1], . . . , tab[j-1]
i←j-1
Tant Que i > 0 Et tab[i] > clé
tab[i+1] ← tab[i]
i←i-1
FinTantQue
tab[i+1] ← clé
FinPour
FinFonction
Exemple
17 -1 3 15 -2
-1 3 15 17 -2
-1 17 3 15 -2
-2 -1 3 15 17
-1 3 17 15 -2
7 / 18

Tri par insertion : coût (1/2)


Fonction tri-insertion(In-Out Variable tab : Tableau d’entiers) : Vide
Variables i, j, clé : Entiers
Pour j allant de 2 à taille(tab) par pas de 1 // n − 1 tours
clé ← tab[j] // k4
// Insère clé dans la séquence tab[1], . . . , tab[j-1]
i←j-1 // 1
Tant Que i > 0 Et tab[i] > clé // tj fois // Soit : ≤ k3 × tj
tab[i+1] ← tab[i] // k1
i←i-1 // k2
FinTantQue
tab[i+1] ← clé // k5
FinPour
FinFonction
tj : nombre de fois que la boucle interne est effectuée pour j donné.
Soit au total :
Xn n
X
Tinsertion (n) = (1 + k4 + k5 + k3 tj ) = (n − 1)k6 + k3 tj
j=2 j=2 8 / 18
Tri par insertion : coût (2/2)
En sommant et en simplifiant tous les coûts précédents on obtient le coût
global C suivant :
n
X
Tinsertion (n) = (n − 1)k6 + k3 tj .
j=2

Analyse dans le meilleur des cas


C’est le cas où le tableau est déjà trié. Donc tj = 1 pour tout j. D’où :

Tbest (n) = k7 × (n − 1).

Analyse dans le pire des cas


C’est le cas où le tableau est trié dans l’ordre inverse. Donc tj = j − 1 pour
tout j. D’où :
Tworse (n) = k8 n2 + k9 n + k10 .
9 / 18

Peut-on faire mieux ?


Tris classiques
Insertion : kn2
Bulle : k 0 n2

Notion de borne inférieure


• Temps nécessaire minimum pour résoudre le problème
• Peuves non constructives en général

Retour sur le tri de n éléments


• On considère le nombre minimum de comparaisons d’éléments
• Un algorithme doit différentier les différentes permutations
• Chaque comparaison coupe le nombre de permutations possibles en
deux
• Il y a n! permutations, il faut donc log2 (n!) étapes au minimum
• Soit de l’ordre de n log2 n étapes
10 / 18
Ordres de grandeur (1/3)
• Le temps de calcul devient un facteur important quand la taille des
instances devient très grande.
• On va donc s’intéresser aux comportement des fonctions de coût C (n)
quand n devient très grand (comportement asymptotique).
Domination asymptotique
Soient F et G des suites à valeurs positives. On dit que F est dominée par
G (en +∞) s’il existe une constante a > 0 et un rang n0 tels que

F (n) ≤ a G (n), ∀n ≥ n0 .

Dans ce cas, on note F = O(G ) (prononcer “grand o”).


Équivalence asymptotique
Soient F et G des suites à valeurs positives. On dit que F et G sont
équivalentes 1 (en +∞) s’il existe des constantes a1 , a2 > 0 et un rang n0
tels que
a1 G (n) ≤ F (n) ≤ a2 G (n), ∀n ≥ n0 .
11 / 18
Dans ce cas, on note F = Θ(G ) (prononcer “grand theta”).
1. Cette notion est différente de celle associée au symbole ∼ en maths.

Ordres de grandeur (2/3)


3.1 Asymptotic notation

c2 g.n/ cg.n/

f .n/
f .n/
c1 g.n/

n n
n0 n0 n
f .n/ D ‚.g.n// f .n/ D O.g.n//
(a) (b)

Figure 3.1 Graphic examples of the ‚, O, and ! notations.


12 / 18 In each part

is the minimum possible value; any greater value would also work. (a) ‚-
Ordres de grandeur (3/3)
• Pour une suite donnée F , on notera
• O(F ) l’ensemble des suites (asymptotiquement) dominées par F .
• Θ(F ) l’ensemble des suites (asymptotiquement) équivalentes à F .
• Pour décrire la classe Θ(F ), il suffit de garder le terme le plus élevé de
F , sans la constante.
Exemples
• 3n2 + 7n + 10 ∈ Θ(n2 )
• 3n2 + 7n + 9 log(n) + 10 ∈ Θ(n2 )
• 3n2 + 7n + 9 n log(n) + 10 ∈ Θ(n2 )
• 5n3 + 9 n log(n) + 7n + 10 ∈ Θ(n3 )
• 9 n log(n) + 7n + 10 ∈ Θ(n log(n))
• 7 × 2n + 5n10 + 9 n log(n) + 7n + 10 ∈ Θ(2n )
• n! + 7 × 2n + 5n10 + 9 n log(n) + 7n + 10 ∈ Θ(n!)

13 / 18

Notion de complexité
Complexité
Soit A un algorithme dont le nombre d’opérations dans le pire des cas est
donné par la suite F . On appelle la classe Θ(F ) la complexité de A.
Complexités remarquables
• Θ(1) : complexité constante, c.a.d. indépendante de la taille des
instances
• Θ(log n) : complexité logarithmique (ou sous-linéaire)
• Θ(n) : complexité linéaire
• Θ(n log n) : complexité quasi-linéaire
• Θ(n2 ) : complexité quadratique
• Θ(np ) : complexité polynomiale
• Θ(2n ) : complexité exponentielle
• Θ(n!) : complexité factorielle

Tri insertion 14 / 18
Complexité quadratique
1200
log(n)
n
n log(n)
1000 n2
2n

800

600

400

200

0
1 2 3 4 5 6 7 8 9 10
15 / 18

Diverses remarques sur la complexité


• Optimiser son code permet de réduire la constante multiplicative.
Optimiser son algorithme permet de réduire la classe de complexité.
• De même, investir dans une machine plus performante n’a un impact
que sur la constante multiplicative (c.f. TD).
• Au sein d’une même classe de complexité, il faut chercher à minimiser
la constante multiplicative.
• La classe Θ(1) est rarement réalisable en pratique. L’accès aux
éléments d’un tableau fournit cependant un exemple important.
• Des algorithmes dont la complexité est sous-linéaire, linéaire ou
quasi-linéaire peuvent être appliqués à des données massives (de
l’ordre de 106 instances et plus).
• Dans la classe Θ(np ), le temps de calcul est une fonction croissante
de l’exposant p. On considère généralement que si p > 3, l’algorithme
ne peut être appliqué à des données massives.
• Les algorithmes de complexité exponentielle ou factorielle n’ont pas
d’intérêt pratique (le temps de calcul associé devient rapidement trop
élevé).
16 / 18
Exemple : inversion d’une matrice
• On souhaite résoudre le système linéaire suivant
Ax = b, avec A ∈ Rn×n inversible.
• Une idée naïve pour résoudre ce système consiste à calculer A−1 puis
calculer le produit matrice-vecteur A−1 b.
• La complexité du produit matrice-vecteur est Θ(n2 ) (n produits
scalaires dans Rn ).
• Le cours de maths fournit la formule suivante pour le calcul de A−1 :
1
A−1 = CT ,
det(A)
où C est la matrice des cofacteurs. Chaque entrée de C nécessite le
calcul du déterminant d’une matrice dans R(n−1)×(n−1) .
• Pour calculer le déterminant d’une matrice dans Rn×n , il faut parcourir
l’ensemble de toutes les permutations {1, . . . , n}, soit n! éléments.
• La complexité de cette méthode d’inversion est donc supérieure à n!.
• Conclusion : formule théorique mais avec peu d’intérêt calculatoire si
n est grand.
17 / 18

Recherche séquentielle
Fonction rechSeq(In Variable tab : Tableau d’entiers,
In Variable clé : Entier) : Booléen
Variable trouvé : Booléen ← faux
Variable i : Entier ← 1
Tant Que (i ≤ taille(tab)) Et (Non trouvé)
Si tab[i] = clé Alors
trouvé ← vrai
FinSi
i ← i + 1
FinTantQue
Retourne trouvé
FinFonction
Complexité
• Nombre d’opérations dans le pire des cas : l’élément n’existe pas.
Donc, Θ(n).
• Ceci est vrai même si le tableau est trié !
• Complexité = Θ(n).
18 / 18

Vous aimerez peut-être aussi