MI2E - 2 E A NNÉE A LGORITHMIQUE G ÉNÉRALE V. Mousseau A LGORITHMIQUE G ÉNÉRALE Partiel - 23/11/2005 - 2 heures aucun document autorisé N˚ carte étudiant : ................................ Exercice 1 : La décomposition en facteurs premiers d’un nombre entier strictement positif consiste à représenter cet entier de la manière suivante : n = ab11 ab22 ...abkk où les ai sont des nombres premiers tels que ai < aj pour i < j et les bj sont des entiers strictement positifs. Par exemple, 84 = 22 × 31 × 71 . La décomposition en facteurs premiers d’un entier est unique. a) Un entier n peut donc être représenté par tableau à double entrée T stockant les ai et les bi : T [i, 1] contenant ai et T [i, 2] contenant bi . Par exemple 84 est représenté par , 2 3 7 2 1 1 Donnez la représentation des entiers 72 et 270. 72 = 2 3 2 3 5 et 270 = 3 2 1 3 1 Soient T1 et T2 les tableaux représentant deux entiers n1 et n2 . On note T aille1 et T aille2 les tailles des tableaux T1 et T2 . Soit la fonction PGCD suivante : fonction PGCD(T1 , T2 : tableau) → entier pgcd, p1 , p2 : entier [1] pgcd ← 1 [2] p1 ← 1 [3] p2 ← 1 [4] tant que (p1 ≤ T aille1 ) et (p2 ≤ T aille2 ) faire [5] si T1 [p1 ,1] = T2 [p2 ,1] [6] alors m ← min(T1 [p1 ,2], T2 [p2 ,2]) [7] pgcd ← pgcd × T1 [p1 ,1]m [8] p1 ← p1 + 1 [9] p2 ← p2 + 1 [10] sinon [11] si T1 [p1 ,1] < T2 [p2 ,1] [12] alors p1 ← p1 + 1 [13] sinon p2 ← p2 + 1 [14] fin si [15] fin si [16] fin tant que [17] retourner(pgcd) b) Faire tourner à la main la fonction PGCD pour les entiers 72 et 84. On prendra soin de noter les valeurs successives des variables pgcd, p1 , p2 ainsi que la valeur du test de la boucle tant que. 72 = 2 3 avec T aille1 = 3 3 2 Instruction p1 p2 p1 1, 2, 3 1 1 4 1 1 6 1 1 7 1 1 8, 9 2 2 4 2 2 6 2 2 7 2 2 8, 9 3 3 4 3 3 17 3 3 et 84 = ≤ T aille1 p2 vrai vrai vrai vrai vrai vrai vrai vrai f aux f aux f aux 2 3 7 avec T aille2 = 3 2 1 1 ≤ T aille2 test bouble tant que m pgcd vrai vrai 1 vrai vrai 1 vrai vrai 2 1 vrai vrai 2 4 vrai vrai 2 4 vrai vrai 2 4 vrai vrai 1 4 vrai vrai 1 12 f aux vrai 1 12 f aux vrai 1 12 f aux vrai 1 12 c) Prouver que la fonction PGCD se termine en un temps fini. L’algorithme se termine dès lors que la boucle tant que s’exécute en un temps fini. Or, le test de cette boucle (p1 ≤ T aille1 ) et (p2 ≤ T aille2 ) devient faux dès lors que (p1 > T aille1 ) ou que (p2 > T aille2 ). De plus, lors de chaque itération, au moins une des deux variables p1 ou p2 est incrémentée d’une unité. Comme ces deux variables sont initialisées à 1, et que T aille1 et T aille2 ont une valeur finie, l’algorithme s’exécutera en un nombre fini d’itérations. Le bloc d’instruction contenu dans la boucle s’exécutant en un temps fini, l’algorithme se terminera en un temps fini. d) Déterminer la complexité de la fonction PGCD Supposons que l’on dispose d’un algorithme Puissance(n1, n2 : entiers)→ nn1 2 qui s’exécute en O(1). Alors la structure conditionnelle <si T1 [p1 ,1] = T2 [p2 ,1]> s’effectue en O(1) (puisque le test booléen et les 2 blocs d’instructions apparaissant dans la structure conditionnelle sont en O(1)). Donc le corps de la boucle tant que s’exécute en O(1). . Le calcul de la complexité revient à déterminer le nombre d’itérations de la boucle tant que. or dans le pire cas, lors de chaque itération, seule une des deux variables p1 ou p2 est incrémentée d’une unité et on exécute alors T aille1 + T aille2 itérations. L’algorithme PGCD est alors en O(T aille1 + T aille2 ) Exercice 2 : On considère deux matrices carrées (d’entiers) P d’ordre n, A et B. Le produit de A par B est une matrice carrée C d’ordre n définie par ci,j = nk=1 ai,k bk,j . Donner un algorithme PROD(A,B) calculant le produit de deux matrices représentées sous forme d’un tableau à deux dimensions. Calculer la complexité de cet algorithme. Doit-on préciser dans quels cas (pire cas, meilleur des cas, cas moyen) cette complexité est obtenue ? 2 PROD(A,B) pour i = 1 à n faire pour j = 1 à nf aire C[i,j] ← 0 ; pour k = 1 à n faire C[i,j] ← C[i,j] + A[i,k]*B[k,j] fin pour fin pour fin pour retourner(C) Chacune des affectations de l’algorithme est en O(1), la complexité correspond donc au nombre de fois que l’instruction <C[i,j] ← C[i,j] + A[i,k]*B[k,j]> est exécutée. Elle est exécutée n3 fois et ceci dans le pire ET dans le meilleur cas. La complexité est donc en Θ(n3 ) Exercice 3 : On considère un type de données abstrait pour manipuler les polynômes. Cet exercice propose d’implémenter certaines opérations de base concernant les polynômes à coefficients entiers sur une variable. Soit E l’ensemble des polynômes à coefficients entiers sur une variable entière x. On considère les trois opérations sur E : – la dérivation : p(x) ∈ E → p′ (x) – l’addition : p(x), q(x) ∈ E → p(x) + q(x) – l’évaluation : p(x) ∈ E, a ∈ Z → p(a) On notera ces opérations Dériv(p), Somme(p, q) et Eval(p, a). Pour les implémenter, on choisit de représenter un polynôme de E par une liste chaînée p = (M1 , ..., Mk ) de monômes, ordonnée par degré croissant, où chaque monôme Mj = (aj , dj ) est caractérisé par son degré dj ∈ N et son coeffiP cient aj ∈ Z∗ . Le polynôme associé à la liste p est alors p(x) = ki=1 ai xdi . Le polynôme nul, noté polynul, est représenté par M0 = (0, 0). x On utilise alors la structure suivante : lien=↑cell cell=Enreg. deg,coef :entier suiv :lien FinEnreg. Ainsi 3x2 + 4x + 7 est représenté par p p • 0 7 • 1 4 • a) Écrire un algorithme implémentant Dériv. 3 2 3 Dériv(p :lien)→ lien p1←p↑.suiv Desallouer(p) Tant que p1↑.suiv 6= Null Faire p1↑.coef ← p1↑.coef * p1↑.deg p1↑.deg ← p1↑.deg-1 p1←p1↑.suiv Fin Tant que Retourner(p1) 4 b) Écrire un algorithme récursif implémentant Somme. Quelle est sa complexité au pire-cas ? Somme(p1,p2 :lien)→ lien c) Soit a ∈ Z et n ∈ N. On suppose que le nombre d’opérations pour calculer an est en Θ(n). Soit p ∈ E. Quelle est la complexité de l’algorithme naïf d’évaluation de p en a, qui évalue d’abord chacun des monômes de p en a et fait la somme des valeurs trouvées ? [1] [2] [3] [4] [5] [6] [7] eval ← 0 Tant que (p 6= Null) puis← xp↑.deg eval ← puis * p↑.coef Répéter Fin Tant que Retourner(eval) P d) Soit p(x) = ni=1 ai xi un polynôme de E de degré n écrit sous sa forme conventionnelle où chaque coefficient aj est négatif, nul ou positif. On considère la suite H0 , ..., Hn de polynômes associés à p : H0 (x) = an , H1 (x) = H0 (x) × x + an−l , ..., Hn (x) = Hn−1 (x) × x + a0 La suite (H0 , ..., Hn ) est la liste des polynômes du schéma de Horner et l’on a formellement p(x) = Hn (x). Déduire du schéma de Horner un algorithme efficace, utilisant une liste doublement chaînée dont vous donnerez la définition, pour évaluer p en x. Quelle est la complexité de cet algorithme ? Exercice 4 : On considère les déclarations et l’algorithme suivants : pt-entier=↑entier lien=↑cell cell=Enreg. ele :entier suiv :lien FinEnreg. L1,L2 :lien p :pt-entier [1] [2] [3] [4] [5] [6] [7] [8] [9] [10] Allouer(p) p↑←10 Allouer(L1), L1↑.ele←1 L2←L1, L2↑.suiv←Null Répéter Allouer(L2) L2↑.suiv←L1 L2↑.ele←L1↑.ele*2 L1←L2 Jusqu’à L1↑.ele>p↑ la mémoire après l’exécution de l’instruction [2] p L1 L2 • 10 la mémoire après l’exécution de l’instruction [4] la mémoire à la fin de l’itération 1 5 p • 10 L1 • L2 • 1 p • 10 L1 • L2 • 2 • la mémoire à la fin de l’itération 2 p • 10 L1 • L2 • 4 • la mémoire à la fin de l’itération 3 p • 10 L1 • L1 • 2 • 1 4 • 2 • 1 8 • 4 • 2 • L2 • 8 • la mémoire à la fin de l’itération 4 p • 10 1 L2 • 16 • 6 1