Adloun

algorithmique (école d'ingénieur) · Chapitre 4 · Application directe du cours

Des jetons dans des boîtes

Répartition optimale d'une ressource · niveau 2

Énoncé

Il y a boîtes de capacité et jetons, . La boîte contenant jetons rapporte , avec et des gains croissants. Les gains sont dans un tableau de lignes et colonnes. Tous les jetons doivent être placés. Sur l'exemple

boîte 020406080
boîte 010204040
boîte 00809090

on dispose de jetons.

  • On note le gain maximum d'une répartition de jetons dans les premières boîtes. Que vaut pour ? Donner la base et l'hérédité de la récurrence.
  • Écrire int[][][] calculerMA(int[][] G, int m) et void aro(int[][] A, int[][] G, int k, int q).
  • Vérifier que et expliquer les deux . Donner et une répartition optimale.
  • Quelle est la complexité en fonction de , et ?

Corrigé

  • Avec boîte, on ne peut placer aucun jeton : et pour (répartition impossible). Supposons le problème résolu : la -ème boîte (numéro ) reçoit jetons, avec , et les autres sont répartis de façon optimale dans les premières boîtes.

Base. ; : .

Hérédité. , :

  • On représente par Integer.MIN_VALUE / 2, qui reste très négatif quand on lui ajoute un gain.

static int[][][] calculerMA(int[][] G, int m) {
    int n = G.length, Q = G[0].length - 1;
    final int MOINS_INFINI = Integer.MIN_VALUE / 2;
    int[][] M = new int[n + 1][m + 1], A = new int[n + 1][m + 1];
    for (int q = 1; q < m + 1; q++) M[0][q] = MOINS_INFINI; // base
    for (int k = 1; k < n + 1; k++)                       // par k croissants
        for (int q = 0; q < m + 1; q++) {
            M[k][q] = MOINS_INFINI;
            for (int x = 0; x < Math.min(q, Q) + 1; x++) { // x jetons dans la k-ème boîte
                int v = G[k - 1][x] + M[k - 1][q - x];
                if (v > M[k][q]) { M[k][q] = v; A[k][q] = x; }
            }
        }                                     // M[k][q] = M(k,q), A[k][q] = arg M(k,q)
    return new int[][][] {M, A};
}

static void aro(int[][] A, int[][] G, int k, int q) {
    if (k == 0) return;                   // aucune boîte : rien à afficher
    int x = A[k][q];                      // jetons de la k-ème boîte
    aro(A, G, k - 1, q - x);              // répartition des q-x autres affichée
    System.out.printf("  boîte %d <-- %d jetons, gain %d%n", k - 1, x, G[k - 1][x]);
}                                         // donc répartition (k,q) affichée
  • La boîte ne peut pas recevoir plus de jetons : placer ou jetons dans la seule première boîte est impossible, d'où . L'exécution donne :

nom : M[1]
valeurs : 0 0 80 90 90 -∞ -∞
griser : 5 6
legende : la boîte 0 seule (Q = 4) ne peut pas recevoir 5 ou 6 jetons

M[3] = [0, 20, 80, 100, 120, 140, 160]
M[2] = [0, 10, 80, 90, 100, 120, 130]
M[1] = [0, 0, 80, 90, 90, -oo, -oo]
M[0] = [0, -oo, -oo, -oo, -oo, -oo, -oo]
Gain maximum M(3,6) = 160
  boîte 0 <-- 2 jetons, gain 80
  boîte 1 <-- 0 jetons, gain 0
  boîte 2 <-- 4 jetons, gain 80

Le glouton, lui, place les quatre premiers jetons dans la boîte (gain marginal contre et ), puis deux dans la boîte : gain seulement.

  • Pour chaque case , la boucle sur fait au plus tours : le calcul est en dans le pire cas, l'affichage en .

100 % gratuit

La suite du chapitre est sur Adloun

Exercice suivant et tuteur

Sans compte : le cours, le premier QCM et 2 minutes de podcast et de vidéo. Exercices et tuteur : inscription gratuite en 30 secondes, sans carte bancaire.

Le cours du chapitre · Tous les exercices du chapitre

Exercice suivant et tuteur →