Multimediální technologie – Cvičení 7


Zadání

Naprogramujte algoritmus pro aritmetické kódování a dekódování. Pomocí tohoto algoritmu zakódujte a dekódujte soubor Cv07_Aritm_data.bin.

Soubory


Řešení

# -*- coding: utf-8 -*-
import os
import struct
import collections
from random import uniform
import matplotlib.pyplot as plt

clear = lambda: os.system('cls')
clear()
plt.close('all')

def getProbabilities(string):
    result = collections.Counter(string)
    result = collections.OrderedDict(sorted(result.items()))
    lastHigh = 0.0
    low = 0.0
    high = 0.0
    for index, item in enumerate(result):
        high = result[item] / float(len(string))
        low = lastHigh
        tmp = high + lastHigh

        lastHigh = tmp

        interval = (round(low, 1), round(tmp, 1))
        result[item] = interval
    return result

def compress(string, probabilities):
    result = ()
    high = 1
    low = 0

    for i, val in enumerate(string):
        current = high - low
        high = low + (current * probabilities[val][1])
        low = low + (current * probabilities[val][0])
    result = (low, high)
    return result

def decompress(num, prob, length):
    string = []

    while length != 0:
        for i, val in enumerate(prob):
            if prob[val][0] <= num <= prob[val][1]:
                string.append(val)

                current = prob[val][1] - prob[val][0]
                num = (num - prob[val][0]) / current


                length -= 1
                if length == 0:
                    return ''.join(string)

    return ' '.join(string)

def getRandom(interval):
    random = uniform(interval[0], interval[1])
    return random

def readFile(filename):
    i = 0
    data = ""

    with open(filename, 'rb') as f:
        while i != os.path.getsize(filename):
            data += "" +str(struct.unpack('B', f.read(1))[0])
            i += 1
    return data

def main():
    stringData = readFile('Cv07_Aritm_data.bin')
    print 'Original data: {0}'.format(stringData)

    probabilities = getProbabilities(stringData)

    compressed = compress(stringData, probabilities)
    print 'Komprimovaná data: {0}'.format(compressed)

    decompressed = decompress(getRandom(compressed), probabilities, len(stringData))
    print 'Dekomprimovaná data: {0}'.format(decompressed)

if __name__ == "__main__":
    main()

Napsat komentář