天天看點

huffman的實作

    #include"iostream"  

    #include "queue"  

    #include "map"  

    #include "string"  

    #include "iterator"  

    #include "vector"  

    #include "algorithm"  

    using namespace std;  

    #define NChar 8 //suppose use 8 bits to describe all symbols  

    #define Nsymbols 1<<NChar //can describe 256 symbols totally (include a-z, A-Z)  

    typedef vector<bool> Huff_code;//8 bit code of one char  

    map<char,Huff_code> Huff_Dic; //huffman coding dictionary  

    class HTree  

    {  

    public :  

        HTree* left;  

        HTree* right;  

        char ch;  

        int weight;  

        HTree(){left = right = NULL; weight=0;ch ='\0';}  

        HTree(HTree* l,HTree* r,int w,char c){left = l; right = r;  weight=w;   ch=c;}  

        ~HTree(){delete left; delete right;}  

        bool Isleaf(){return !left && !right; }  

    };  

    class Compare_tree  

    {  

    public:  

        bool operator () (HTree* t1, HTree* t2)  

        {  

            return t1->weight> t2->weight;  

        }  

    };  

    HTree* BuildTree(int *frequency)  

    {  

        priority_queue<HTree*,vector<HTree*>,Compare_tree> QTree;  

        //1st level add characters  

        for (int i=0;i<Nsymbols;i++)  

        {  

            if(frequency[i])  

                QTree.push(new HTree(NULL,NULL,frequency[i],(char)i));            

        }  

        //build  

        while (QTree.size()>1)  

        {  

            HTree* lc  = QTree.top();  

            QTree.pop();  

            HTree* rc = QTree.top();  

            QTree.pop();  

            HTree* parent = new HTree(lc,rc,lc->weight+rc->weight,(char)256);  

            QTree.push(parent);  

        }  

        //return tree root  

        return QTree.top();  

    }  

    void Huffman_Coding(HTree* root, Huff_code& curcode)  

    {  

        if(root->Isleaf())  

        {  

            Huff_Dic[root->ch] = curcode;  

            return;  

        }  

        Huff_code lcode = curcode;  

        Huff_code rcode = curcode;  

        lcode.push_back(false);  

        rcode.push_back(true);  

        Huffman_Coding(root->left,lcode);  

        Huffman_Coding(root->right,rcode);  

    }  

    int main()  

    {  

        int freq[Nsymbols] = {0};  

        char *str = "this is the string need to be compressed";  

        //statistic character frequency  

        while (*str!='\0')  

            freq[*str++]++;  

        //build tree  

        HTree* r = BuildTree(freq);  

        Huff_code nullcode;  

        nullcode.clear();  

        Huffman_Coding(r,nullcode);  

        for(map<char,Huff_code>::iterator it = Huff_Dic.begin(); it != Huff_Dic.end(); it++)  

        {  

            cout<<(*it).first<<'\t';  

            std::copy(it->second.begin(),it->second.end(),std::ostream_iterator<bool>(cout));  

            cout<<endl;  

        }

}