LATEX
LATEX
LATEX
Mini projet
Programmation dynamique, Le
problème de SAC-à-DOS
Réalisé par :
M. NABGAOUI Khalid Encadré par :
M. AHTI Imad Pr. OUCHAOU Brahim
Promotion : 2023/2024
Table des matières
i
0.1. INTRODUCTION GÉNÉRALE
0.1.3 Méthodologie
Pour atteindre ces objectifs, notre approche repose sur une méthodologie rigoureuse.
Nous avons mené une recherche approfondie, recueilli des données pertinentes, et utilisé
des outils d’analyse avancés pour garantir la fiabilité et la pertinence de nos conclusions.
1
0.2. VISION GLOBALE SUR LA PROGRAMMATION DYNAMIQUE
2
0.2. VISION GLOBALE SUR LA PROGRAMMATION DYNAMIQUE
Algorithmes de Chemin le Plus Court : Les algorithmes de chemin le plus court, tels
que l’algorithme de Bellman-Ford, utilisent la programmation dynamique pour trouver
les chemins les plus courts dans un graphe pondéré.
3
0.2. VISION GLOBALE SUR LA PROGRAMMATION DYNAMIQUE
0.2.4.2 Inconvénients
• Complexité Conceptuelle : Comprendre et concevoir des solutions en utilisant
la programmation dynamique peut être complexe, en particulier pour des problèmes
novateurs ou pour des personnes peu familières avec cette approche.
4
0.3. PRINCIPES FONDAMENTAUX DE LA PROGRAMMATION DYNAMIQUE
5
0.3. PRINCIPES FONDAMENTAUX DE LA PROGRAMMATION DYNAMIQUE
problème global.
Cette relation, souvent dérivée de la sous-structure optimale, fournit le modèle mathé-
matique qui guide la décomposition du problème en sous-problèmes et la reconstruction
de la solution optimale à partir de ces sous-solutions. La clarté et la précision de la re-
lation de récurrence sont cruciales pour garantir la validité et l’efficacité de l’algorithme
de programmation dynamique.
6
0.4. LE PROBLÈME DU SAC À DOS ILLIMITÉ
∑
max xi pj
j∈N
∑
s.t. xj w j ≤ C
j∈N
xj ∈ N ∀j ∈ N
UKP fait partie d’une famille de problèmes appelés problèmes de sac à dos. On l’ap-
pelle illimité car chaque type d’élément dans N peut être utilisé autant de fois que néces-
saire. D’autres variantes de problèmes de sac à dos incluent des problèmes dans lesquels
seul un nombre limité d’éléments de chaque type peut être utilisé (problème de sac à dos
limité) et des problèmes dans lesquels chaque type d’élément ne peut être utilisé qu’une
seule fois (problème de sac à dos 0-1).
Même s’il existe un nombre illimité d’éléments disponibles de chaque type, la quantité
d’éléments dans une solution est naturellement limitée par la capacité du sac à dos. Ainsi,
un solveur pour le problème du sac à dos borné résout également l’UKP si nous fixons
les limites b ; sur chaque article i (le nombre maximum de chaque type d’article autorisé
dans le sac à dos) comme la capacité C divisée par son poids w. La même chose peut
être dite pour le problème du sac à dos 0-1 : une instance UKP peut être transformée en
une instance du problème du sac à dos 0-1 si nous créons b copies de chaque élément i.
L’utilisation des transformations susmentionnées pour résoudre les instances UKP montre
de mauvaises performances en pratique. Afin d’utiliser un solutionneur de problèmes de
sac à dos 0-1, un grand nombre d’éléments doivent être créés, en particulier lorsque la
capacité du sac à dos est grande, ce qui augmente le temps de traitement et la quantité de
mémoire requise. Il existe également certaines propriétés de l’UKP (à savoir la dominance
et la périodicité) qui ne sont pas présentes dans d’autres variantes. De telles propriétés
peuvent être exploitées par un algorithme spécifique à l’UKP.
Il existe deux méthodes classiques et exactes pour résoudre l’UKP : Branch Bound
et Dynamic Programming. Dans ce chapitre, les deux techniques sont expliquées. Ces
techniques exploitent la propriété de domaine pour résoudre UKP.
7
0.4. LE PROBLÈME DU SAC À DOS ILLIMITÉ
4. Problème du Sac à Dos Bidimensionnel :Les objets ont deux attributs (par
exemple, poids et volume) et le sac à dos a deux capacités.
Gestion des Stocks : Maximiser la valeur des produits stockés tout en respectant les
contraintes d’espace d’entreposage.
8
0.5. IMPLÉMENTATION D’UN ALGORITHME DE
PROGRAMMATION DYNAMIQUE POUR LE SAC À DOS
0.5 Implémentation d’un algorithme de
programmation dynamique pour le sac à dos
0.5.1 Example
Toute formulation commence par un énoncé des données. Dans notre cas, nous avons
un sac à dos de poids maximal W et n objets. Pour chaque objet i, nous avons un poids
wi et une valeur pi .
Pour quatre objets (n = 4) et un sac à dos d’un poids maximal de 30 kg(W = 30),
nous avons par exemple les données suivantes :
Objets 1 2 3 4
pi 7 4 3 3 �
Wi 13 12 8 10
Ensuite, il nous faut définir les variables qui représentent en quelque sorte les actions ou
les décisions qui amèneront à trouver une solution. On définit la variable xi associée à un
objet i de la façon suivante : xi = 1 si l’objet i est mis dans le sac, et xi = 0 si l’objet i
n’est pas mis dans le sac.
Dans notre exemple, une solution réalisable est de mettre tous les objets dans le sac à
dos sauf le premier, nous avons donc : x1 = 0, x2 = 1, x3 = 1, etx4 = 1.
Puis il faut définir les contraintes du problème. Ici, il n’y en a qu’une : la somme des
poids de tous les objets dans le sac doit être inférieure ou égale au poids maximal du sac
à dos.
Cela s’écrit : x1 .w1 + x2 .w2 + x3 .w3 + x4 .w4 ≤ W
ou plus généralement pour n objets :
∑
n
xi .wi ≤ W
i=1
Pour vérifier que la contrainte est respectée dans notre exemple, il suffit de calculer cette
somme : 0×13 + 1×12 + 1×8 + 1×10 = 30, ce qui est bien inférieur ou égal à 30, donc
la contrainte est respectée. Nous parlons alors de solution réalisable. Mais ce n’est pas
nécessairement la meilleure solution.
Enfin, il faut exprimer la fonction qui traduit notre objectif : maximiser la valeur totale
des objets dans le sac.
Pour n objets, cela s’écrit :
∑
n
max xi .pi
i=1
Dans notre exemple, la valeur totale contenue dans le sac est égale à 10. Cette solution
n’est pas la meilleure, car il existe une autre solution de valeur plus grande que 10 : il faut
prendre seulement les objets 1et2 qui donneront une valeur totale de 11. Il n’existe pas de
meilleure solution que cette dernière, nous dirons alors que cette solution est optimale.
9
0.5. IMPLÉMENTATION D’UN ALGORITHME DE
PROGRAMMATION DYNAMIQUE POUR LE SAC À DOS
0.5.2 méthodes de résolution de problème de sac à dos
Il existe deux grandes catégories de méthodes de résolution de problèmes d’optimi-
sation combinatoire : les méthodes exactes et les méthodes approchées. Les méthodes
exactes permettent d’obtenir la solution optimale à chaque fois, mais le temps de calcul
peut être long si le problème est compliqué à résoudre. Les méthodes approchées, encore
appelées heuristiques, permettent d’obtenir rapidement une solution approchée, donc pas
nécessairement optimale. Nous allons détailler un exemple d’algorithme de résolution de
chaque catégorie.
• DEBUT
• calculer la valeur (pi / wi) pour chaque objet i,
• trier tous les objets par ordre décroissant de cette valeur,
• sélectionner les objets un à un dans l’ordre du tri et ajouter l’objet sélectionné dans
le sac si le poids maximal reste respecté.
• FIN
• Première étape :
Objets 1 2 3 4
�
pi /Wi 0.54 0.33 0.37 0.30
10
0.5. IMPLÉMENTATION D’UN ALGORITHME DE
PROGRAMMATION DYNAMIQUE POUR LE SAC À DOS
cause une décision prise auparavant. Ici, lorsque l’objet 2 ne peut pas entrer dans
le sac, l’algorithme n’essaie pas d’enlever l’objet 3 du sac pour y mettre l’objet 2 à
sa place.
Une PSE est un algorithme qui permet d’énumérer intelligemment toutes les solutions
possibles. En pratique, seules les solutions potentiellement de bonne qualité seront énu-
mérées, les solutions ne pouvant pas conduire à améliorer la solution courante ne sont pas
explorées. Pour représenter une PSE, nous utilisons un « arbre de recherche » constitué :
Dans notre exemple, les nœuds représentent une étape où un certain nombre d’objets
auront été mis dans le sac, d’autres laissés en dehors du sac, et d’autres objets pour
lesquels aucune décision n’a encore été prise. Chaque arc indique l’action de mettre un
objet dans le sac ou au contraire de ne pas le mettre dans le sac. La figure suivante
représente une partie de l’arbre de recherche.
11
0.5. IMPLÉMENTATION D’UN ALGORITHME DE
PROGRAMMATION DYNAMIQUE POUR LE SAC À DOS
À partir d’une étape N , l’algorithme construit deux nouvelles étapes : dans celle de
gauche, on conserve toutes les décisions prises à l’étape N et on ajoute la décision de mettre
un nouvel objet (ici l’objet i) dans le sac ; dans celle de droite, on conserve également
toutes les décisions prises à l’étape N et on ajoute la décision de ne pas mettre l’objet i.
L’arbre de recherche commence par un seul nœud, où aucune décision n’a été prise pour
les objets. Une fois tous les objets sélectionnés, les nœuds finaux, aussi appelés nœuds
feuilles, représentent chacun une solution finale. La figure suivante reprend l’exemple
précédent et représente l’arbre de recherche induit.
Les nœuds en rouge représentent une solution impossible. Par exemple, pour le nœud
tout à gauche en rouge, il est impossible de prendre les trois premiers objets à cause
du poids maximal à ne pas dépasser. Il n’est donc pas nécessaire de développer l’étape
suivante avec le dernier objet. Les nœuds en bleu sont des nœuds feuilles correspondant à
une solution réalisable. À la fin de l’algorithme, il suffit de calculer la valeur du sac pour
chaque nœud feuille et de prendre la solution avec la plus grande valeur. La figure n’expose
pas tous les nœuds feuilles, étant donné qu’il y en a beaucoup seulement avec 4 objets.
Et plus le nombre d’objets augmente, plus le nombre de feuilles augmente rapidement.
On parle de croissance exponentielle.
• une borne inférieure est une valeur minimum de la fonction objectif. Autrement dit,
c’est une valeur qui est nécessairement inférieure à la valeur de la meilleure solution
possible. Dans notre cas, une configuration du sac réalisable quelconque fournit une
borne inférieure.
12
0.5. IMPLÉMENTATION D’UN ALGORITHME DE
PROGRAMMATION DYNAMIQUE POUR LE SAC À DOS
• une borne supérieure est une valeur maximale de la fonction objectif. Autrement
dit, nous savons que la meilleure solution a nécessairement une valeur plus petite.
Dans notre cas, nous savons que la valeur de la meilleure solution est nécessairement
inférieure à la somme des valeurs de tous les objets (comme si on pouvait tous les
mettre dans le sac).
Il est important de noter que cette complexité peut être acceptable pour des instances
de problèmes de taille modérée, mais elle peut devenir prohibitivement élevée pour des
instances plus grandes. Dans de tels cas, des techniques d’optimisation ou d’autres va-
riantes de l’algorithme peuvent être envisagées.
13
0.6. MODÈLES DE CHEMINS : ÉQUATION DE RÉCURRENCE ET
ALGORITHME
0.6 Modèles de chemins : équation de récurrence et
algorithme
Equation de Bellman dans un graph sans circuit
�
On suppose un graphe pondéré dirigé, étiqueté G = (V, E) où V représente les sommets
et E représente les arêtes du graphe. Le graphe se compose de sept sommets étiquetés A,
B, C, D, E, F et G.
14
0.6. MODÈLES DE CHEMINS : ÉQUATION DE RÉCURRENCE ET
ALGORITHME
Vous pouvez observer qu’il existe des nœuds étiquetés avec des paires de nombres
(comme ”0,0”, ”1,0”, ”2,1”, etc.), et ces nœuds sont disposés en niveaux ou couches de
gauche à droite. Chaque nœud est connecté à un ou plusieurs nœuds de la couche suivante
par des bords dirigés représentés par des flèches. Il y a un nœud spécial appelé « s » à
l’extrême gauche, qui désigne généralement la source ou le point de départ. À l’extrême
droite, il y a un autre nœud spécial appelé « t », qui représente généralement la cible ou
le point final.
f ∗ (C, 0) ∀C ≥ 0
15
0.6. MODÈLES DE CHEMINS : ÉQUATION DE RÉCURRENCE ET
ALGORITHME
f ∗ (C, i) = max(f ∗ (C − Wi , i − 1) + vi , f ∗ (C, i − 1)) n = 5 W = 10
v1 v2 v3 v4 v5 w1 w2 w3 w4 w5
� �
3 5 6 7 10 2 3 4 4 8
wi 0 2 3 4 4 8
vi 0 3 5 6 7 10
c|i 0 1 2 3 4 5
0 0 0 0 0 0 0
1 0 0 0 0 0 0
2 0 3 3 3 3 3
3 0 3 5 5 5 5
4 0 3 5 6 7 7
5 0 3 8 8 8 8
6 0 3 8 9 10 10
7 0 3 8 11 12 12
8 0 3 8 11 13 13
9 0 3 8 14 15 15
10 0 3 8 14 16 16
16
0.6. MODÈLES DE CHEMINS : ÉQUATION DE RÉCURRENCE ET
ALGORITHME
POUR TOUT i de 1 à n :
POUR TOUT C de 0 à W :
SI Wi ≤ C :
SI f [C − wi, i − 1] + vi ≥ f [C, i]
p[C, i] = C
SINON : p[C, i] = C
f [C, i] = max(f [C − wi , i − 1] + vi , f [C, i − 1])
SINON Wi ≤ C :
p[C, i] = C
f [C, i] = f [C, i − 1]
wi 0 2 3 4 4 8
vi 0 3 5 6 7 10
C�i 0 1 2 3 4 5
0 -1 0 0 0 0 0
1 -1 1 1 1 1 1
2 −1 0 2 2 2 2
3 −1 1 0 3 3 3
4 −1 2 1 0 0 4
5 −1 3 2 5 5 5
6 −1 4 3 2 2 6
7 −1 5 4 3 3 7
8 −1 6 5 4 4 8
9 −1 7 6 5 5 9
10 −1 8 7 6 6 10
Algorithme récursif
17
0.7. CONCLUSION
0.7 Conclusion
La résolution du problème du sac à dos à travers l’application de l’algorithme de program-
mation dynamique a démontré son efficacité dans la recherche de solutions optimales. À
travers cette étude de cas spécifique, nous avons exploré les aspects fondamentaux du
problème, formulé une approche algorithmique, et implémenté cette dernière pour une
application pratique liée à la gestion d’un sac à dos de voyage.
Cependant, il est essentiel de souligner que la performance de l’algorithme peut être in-
fluencée par la taille du problème et la capacité du sac à dos. Des instances de problèmes
plus importantes peuvent nécessiter des adaptations ou des améliorations de l’algorithme
pour maintenir une efficacité pratique.
18