首先我們看一下相關的一些概念。
路徑長度:從樹中乙個節點到另外乙個節點之間的分支構成兩個節點之間的路徑,,路徑上的分支數目稱為路徑長度。如圖中的數字就為路徑長度。
樹的路徑長度就是從樹根到每乙個節點的路徑的長度總和。上圖二叉樹的樹路徑長度為1+1+2+2+2+2+3+3=16。那麼根據這樣可以得出當節點一樣的兩棵樹,完全二叉樹時其樹路徑長度最小。當為單叉樹樹時其樹的路徑長度最大。
帶權路徑長度:每個葉子的權與根到該葉子的路徑長度的乘積之和,記為wpl。
上圖二叉樹的wpl為:5*3+15*3+40*2+30*2+10*2=220。
赫夫曼樹:在具有n個相同的各二叉樹中,wpl最小的二叉樹。
赫夫曼樹的特點:
完全二叉樹並不一定是赫夫曼樹。
在赫夫曼樹中,權值大的節點離根近。
赫夫曼樹不唯一,但wpl一定相等。
那麼如何構建一棵赫夫曼樹???
先把有權值的葉子結點按照從小到大的順序進行排列。a5,e10,b15,d30,c40。
取頭兩個最小權值的節點作為乙個新節點n1的兩個子節點,相對較小的是左孩子。新節點兩個葉子權值的和為15。
將n1插入到序列中,此時序列為n1 15,b15,d30,c40。
重複步驟2,將n1和b取出來,作為n2的子節點。n2的權值為30。
n2替換n1與b,此時序列為n2 30,d30,c40。
重複步驟2,建立乙個新節點n3。
n3替換n2,d。序列此時為c40,n3 60。
重複步驟2,建立乙個新節點t(根節點),c為左孩子,此時赫夫曼樹建立完成。
此時計算其wpl=205。所以此時這棵樹為最優的赫夫曼樹。
根據上面的步驟我們可以總結出赫夫曼演算法。
根據給定的n個權值構成n棵二叉樹的集合f=;其中每棵二叉樹只有乙個帶權的根節點,其左右子樹均為空。
在f中選取兩棵根節點的權值最小的樹作為左右子樹構造一棵新的二叉樹,且新的二叉樹的根節點的權值為其左右子樹上根節點的權值之和。
在f中刪除這兩個子樹,同時將新的二叉樹放入f中。
重複2和3直到f只有一棵樹為止,及赫夫曼樹。
赫夫曼編碼:為了解決當年遠距離通訊(電報)的資料傳輸的最優化問題。
步驟:將字母的頻率設定為權值
將這些字母按照權值生成赫夫曼樹
約定左分支表示字元『0』,右分支表示字元『1』,則可以用從根結點到葉子結點的路徑上的分支字串作為該葉子結點字元的編碼。
這是種不等長編碼,將頻率高的字母用較短的二進位制表示,頻率低的則用較長二進位制表示,以起到壓縮長度的作用。不等長編碼必須滿足字首碼性質:
字首碼:對每乙個字元規定乙個0,1串作為其**,並要求任一字元的**都不是其他字元**的字首。這種編碼稱為字首碼。
而使用赫夫曼樹生成的字母編碼必定符合字首碼條件。
我們如果想將abcdef傳輸給別人,那麼我們可以用相應的二進位制表示:
每個字母傳輸的頻率都是不同的。
那麼我們假設六個字母的頻率為a27,b8,c15,d15,e30,f5。那麼我們可以用赫夫曼樹來規劃它。
我們將權值的左分支改為0,右分支改為1。那麼我們可以得到下表:
我們可以發現資料被壓縮了,節省了大約17%的傳輸成本。
規定赫夫曼樹的左分支代表0,右分支代表1,則從根節點到葉子節點所經過的路徑分支組成的0和1的序列便為該節點對應字元的編碼,這就是赫夫曼編碼。
構造赫夫曼樹(最優二叉樹)
例如,有權值分別為 5 10 15 20 25 40的結點,根據以上演算法構造出乙個哈夫曼樹。取這六個樹中最小的兩個樹5 10連成乙個二叉樹,其權值為15 此時森林裡的樹變為15 5 10 15 20 25 40。取這五個樹中最小的兩個樹 15 5 10 15 構成乙個新的二叉樹30 5 10 15...
赫夫曼樹與赫夫曼編碼
問題描述 利用huffman編碼進行通訊可以大大提高通道利用率,縮短資訊傳輸時間,降低傳輸成本。但是,這要求在傳送端通過乙個編碼系統對待傳資料預先編碼,在接受端將傳來的資料編碼進行解碼 復原 對於有些通道,每端都需要乙個完整的編 解碼系統。試為這樣的資訊收發站編寫乙個huffman的編 解碼系統。給...
赫夫曼樹和赫夫曼編碼
赫夫曼樹 1 先把有權值的葉子節點按照從小到大的順序排成乙個有序序列,即 a 5 e 10 b 15 d 30 c 40 2 取前兩個權值最小的結點即a 5 和e 10 作為乙個新的結點n1的兩個子節點,結點權值較小的作為左結點,即a為左結點,e為右結點,n1的權值為兩個結點權值的和,即5 10 1...