Sunteți pe pagina 1din 4

Compresia Huffman

1. Coninutul lucrrii

n lucrare este prezentat unul dintre cei mai utilizai algoritmi de compresie.

2. Consideraii teoretice

Compresia este procesul de minimizare a spaiului ocupat sau a timpului necesar transmiterii unei
anumite cantiti de informaie.
Aprecierea cantitativ a compresiei realizate se face utiliznd factorul de compresie definit ca: F
c
=n
u
/n
c
,
unde n
u
este lungimea n bii a mesajului iniial i n
c
lungimea dup compresie.
Determinarea codurilor Huffman pentru caracterele unui sir de intrare este una dintre aplicatiile
binecunoscute ale arborilor binari. Aceste coduri vor putea fi apoi folosite pentru codificarea sirului pe un
numar de biti semnificativ mai mic decat cel initial. Daca pe post de sir de caractere este folosit un fisier,
codurile Huffman pot ajuta la compresia fisierului respectiv (reprezentarea continutului sau pe un numar de biti
mai mic decat in mod normal).

De exemplu, ntr-un fisier apar 6 caractere cu urmtoarele frecvene:
a (45), b(13), c(12), d(16), e(9), f(5)
Codurile Huffman pentru aceste caractere sunt:
a= 0, b=101, c=100, d=111, e=1101, f=1100
Fiecare cod Huffman ncepe cu un prefix distinct, ceea ce permite recunoaterea lor la decompresie; de
exemplu fisierul comprimat 001011101 va fi decodificat ca 0/0/101/1101 = aabe.
Problema este de a stabili codul fiecrui caracter funcie de probabilitatea lui de apariie astfel nct
numrul total de bii folosii n codificarea unui ir de caractere s fie minim. Pentru generarea codurilor de
lungime variabil se folosete un arbore binar n care fiecare nod neterminal are exact doi succesori.
Pentru exemplul dat arborele de codificare cu frecvenele de apariie n nodurile neterminale i cu
literele codificate n nodurile terminale este :

Se observ introducerea unor noduri intermediare notate cu cifre.
Pentru codificare se parcurge arborele ncepnd de la radacin i se adaug cte un bit 0 pentru un
succesor la stnga i cte un bit 1 pentru un succesor la dreapta.
Algoritmul genereaz arborele de codificare ncepnd de jos n sus, alegnd arborii cu frecvenele cele mai
sczute i grupndu-le ntr-un nou arbore avnd ca informaie suma frecvenelor celor doi subarbori ataai.

Algoritmul de compresie Huffman trebuie s respecte urmtorii pai:
1) Se calculeaz frecvenele de apariie ale simbolurilor.
2) Se construiesc n arbori cu frecvenele obinute.
3) Se aleg arborii cu frecvenele cele mai scazute i se grupeaz ntr-un nou arbore avnd ca informaie
suma frecvenelor celor doi subarbori ataai.
4) Se aplic pasul 3 pn se ajunge la un singur arbore.
5) Din arborele Huffman, se completeaz dicionarul de coduri prin parcurgerea n adncime a acestuia.
6) Folosind dicionarul de coduri, se codeaz mesajul.

Pentru implementarea algoritmului de compresie vei folosi urmtoarea structur:

typedef struct nod
{
int freq;
bool free;
int st,dr,parinte;
};

Funciile ajuttoare sunt:

void initHuff()
{
for(int i=0;i<255;i++)
{
huff[i].dr=-1;
huff[i].st=-1;
huff[i].parinte=-1;
huff[i].free=true;
}

}

void computeFreq(char *text)
{
int l=strlen(text);
for(int i=0;i<l;i++)
{
huff[text[i]].freq++;
}
}

int findSmaller(int n, int j)
{
int smaller=INT_MAX;
int index=0;
for(int i=0;i<n;i++)
if(huff[i].free)
if(smaller>huff[i].freq&&i!=j)
{
smaller=huff[i].freq;
index=i;
}
return index;
}

void buildHuffmanTree()
{
int n=128;
while(n<255)
{
int i=findSmaller(n,-1);
int j=findSmaller(n,i);
huff[n].freq=huff[i].freq+huff[j].freq;
huff[n].free=true; huff[n].st=i; huff[n].dr=j;
huff[i].free=false; huff[j].free=false;
huff[i].parinte=n; huff[j].parinte=n;
n++;
}
}

void buildDictionary()
{
int nod, parent;
char cod[128];
for(int i=0;i<128;i++)
{
nod=i;
strcpy(codes[i],"");
while(nod!=254)
{
parent=huff[nod].parinte;
if(huff[parent].st==nod)
{
strcpy(cod,codes[i]); strcpy(codes[i],"0"); strcat(codes[i],cod);
}
else
{
strcpy(cod,codes[i]);strcpy(codes[i],"1"); strcat(codes[i],cod);
}
nod=parent;
}
}

}

void compressHuffman(char* text, char * buffer, int & d)
{
int l=strlen(text);
d=0;
char cod[128], byte=0, biti=0;
for(int i=0;i<l;i++)
{
char c=text[i];
strcpy(cod,codes[c]);
for(int j=0;j<strlen(cod);j++)
{
byte=2*byte+cod[j]-'0';
biti++;
if(biti==8)
{
buffer[d]=byte;
d++;
biti=0;
byte=0;
}
}
}
buffer[d]=byte<<(8-biti);
d++;
buffer[d]=biti;
d++;
}

Pentru desfurarea laboratorului, implementai algoritmul de decompresie Huffman respectnd
urmtorii pai:

1) Eventual se reconstruiete dictionarul Huffman pe baza frecvenelor de apariie ale simbolurilor.
2) Se iniializeaz un cuvant de cod vid.
3) Se adaug cuvantului de cod urmtorul bit i se caut un simbol n dicionar corespunztor codului.
4) Dac nu se gsete n dicionar, se revine la pasul 3.
5) Dac se gsete, se afieaz simbolul, napoi la pasul 2.
6) Se repet paii 2-5 pn la finalul fluxului binar.


3. Mersul lucrrii
3.1 Se citete de la tastatur o expresie matematic n form postfixat, sub forma unui ir de caractere.
S se construiasc arborele corespunztor acestei expresii, fiecare nod coninnd un operator sau un operand.
3.2 S se tipreasc expresia de la punctul 3.1. n form postfixat i infixat.
3.3 S se evalueze expresia matematic de la punctul 3.1.
3.4 S se evalueze un arbore care conine n noduri constantele 0 i 1 i operatorii AND, OR, NOT.

S-ar putea să vă placă și