diff --git a/src/compress.c b/src/compress.c index b5385eb..ef73e41 100644 --- a/src/compress.c +++ b/src/compress.c @@ -33,9 +33,9 @@ double* _createFrequencies(FILE* file, size_t* total) { frequencies[i] = 0; } + // Lecture du fichier caractère par caractère et comptage int current; - // Lecture du fichier caractère par caractère et comptage while ((current = fgetc(file)) != EOF) { assert(current >= 0 && current < NUM_CHARS); frequencies[current]++; @@ -69,7 +69,11 @@ void _encodeFromTable(char** labels, FILE* source, WriteBuffer* output) { } void compress(FILE* source, FILE* dest) { - // Étape 1 : calcul des fréquences de chaque caractère + // ÉTAPE 1 : calcul des fréquences d'apparition de chaque caractère + // dans le fichier source. Ce programme prend le terme caractère au sens + // restreint d'octet. Dans le cas où l'on compresse des fichiers Unicode + // utilisant des caractères sur plusieurs octets, on aura donc une + // compression moins optimale. // FIXME: éviter la division par zéro pour les fichiers vides printVerbose("Calcul des fréquences d'apparition des caractères.\n"); size_t start_bytes = 0; @@ -79,7 +83,8 @@ void compress(FILE* source, FILE* dest) { printFrequenciesTable(frequencies, NUM_CHARS); } - // Étape 2 : construction d'un arbre de Huffman pour les fréquences + // ÉTAPE 2 : construction d'un arbre de Huffman correspondant aux + // fréquences d'apparition des caractères // FIXME: éviter les arbres malformés avec les fichiers ne contenant qu'un // seul type de caractère printVerbose("\nConstruction de l'arbre de Huffman.\n"); @@ -92,7 +97,9 @@ void compress(FILE* source, FILE* dest) { printTree(tree); } - // Étape 3 : calcul de la clef de codage (coloration de l'arbre) + // ÉTAPE 3 : calcul de la clef de codage en étiquettant les chaque feuille + // de l'arbre. Pour chaque sommet traversé, s'il est le fils gauche de son + // parent, l'étiquette est augmentée d'un '0', sinon elle l'est d'un '1' printVerbose("\nÉtiquetage des feuilles de l'arbre.\n"); char** labels = createTreeLabels(tree); @@ -100,7 +107,9 @@ void compress(FILE* source, FILE* dest) { printLabelsTable(labels, NUM_CHARS); } - // Étape 4 : écriture des données compressées vers la sortie + // ÉTAPE 4 : écriture des données compressées vers la sortie. Les données + // écrites permettent de restituer le fichier originel : nombre de + // caractères stockés, arbre de Huffman et données compressées brutes WriteBuffer output = createWriteBuffer(dest); printVerbose("\nÉcriture des données compressées.\n"); @@ -116,15 +125,14 @@ void compress(FILE* source, FILE* dest) { _encodeFromTable(labels, source, &output); flushBuffer(&output); - // Affichage des statistiques de compression + // ÉTAPE 5 : affichage des statistiques de compression et fin size_t end_bytes = sizeof(start_bytes) + getFlushedCount(&output); - double gain = (start_bytes - end_bytes) / (double) start_bytes * 100; + double gain = ((double) start_bytes - end_bytes) / start_bytes * 100; printVerbose("Taille originelle : %d octets.\n", start_bytes); printVerbose("Taille compressée : %d octets.\n", end_bytes); printVerbose("Gain : %.2f %% !\n", gain); - // Nettoyage des objets freeTree(tree); freeTreeLabels(labels); labels = NULL;