1.5.4. Кодовое переполнениеБолее серьезную проблему может создать кодовое переполнение. Это случится, если на дерево поступит слишком много символов и оно станет слишком высоким. Сами коды не хранятся на дереве, так как они меняются все время, и компрессор должен вычислять код символа Рис. 1.16. Адаптивный код Хаффмана, пример: часть I. 1. Кодер должен обнаружить символ 2. Если Рис. 1.16. Адаптивный код Хаффмана, пример: часть II. 3. Если Рис. 1.16. Адаптивный код Хаффмана, пример: часть III. Правильное решение может заключаться в накоплении битов кода в связанном списке, к которому можно добавлять новые узлы. Тогда ограничением будет служить лишь объем доступной памяти. Это общее решение, но медленное. Другое решение состоит в накапливании кода в длинной целой переменной (например из 50 разрядов). При этом следует документировать программу ограничением в 50 бит для максимальной длины кодов. Рис. 1.16. Адаптивный код Хаффмана, пример: часть IV. К счастью, эта проблема не оказывает влияние на процесс декодирования. Декодер читает сжатый код бит за битом и использует каждый бит, чтобы идти шаг за шагом влево или вправо вниз по дереву, пока он не достигнет листа с символом. Если листом служит esc код, декодер прочтет несжатый символ из сжатого файла (и добавит этот символ на дерево). В противном случае несжатый символ будет на этом листе дерева. Пример: Применим адаптивное кодирование Хаффмана к строке «sir_sid_is». Для каждого входного символа найдены код на выходе, дерево после добавления этого символа, дерево после модификации (если необходимо), а также пройденные узлы слева направо снизу вверх. Рис. 1.16 показывает начальное дерево и как оно изменялось за 11 шагов от (a) до (k). Обратите внимание на то, как символ esc получает все время разные коды, и как разные символы перемещаются по дереву, меняя свои коды. Код 10, например, кодирует символ «i» на шагах (f) и (i), этот же код присваивается символу «s» на шагах (е) и (j). Пустой символ имеет код 011 на шаге (h), но он же имеет код 00 на шаге (k). На выходе кодера будет строка «s0i00r100_1010000d011101000». Общее число битов равно
|