哈夫曼樹權值計算


  1 #include <iostream>
  2 #include <iomanip>
  3 using namespace std;
  4 
  5 //哈夫曼樹的存儲表示
  6 typedef struct
  7 {
  8     int weight;    // 權值
  9     int parent, lChild, rChild;    // 雙親及左右孩子的下標 
 10 }HTNode, *HuffmanTree;
 11 
 12 
 13 // 選擇權值最小的兩顆樹 
 14 void SelectMin(HuffmanTree hT, int n, int &s1, int &s2)
 15 {
 16     s1 = s2 = 0;
 17 
 18     int i;
 19     for(i = 1; i < n; ++ i){
 20         if(0 == hT[i].parent){
 21             if(0 == s1){
 22                 s1 = i;
 23             }
 24             else{
 25                 s2 = i;
 26                 break;
 27             }
 28         }
 29     }
 30     if(hT[s1].weight > hT[s2].weight){
 31         int t = s1;
 32         s1 = s2;
 33         s2 = t;
 34     }
 35 
 36     for(i += 1; i < n; ++ i){
 37         if(0 == hT[i].parent){
 38             if(hT[i].weight < hT[s1].weight){
 39                 s2 = s1;
 40                 s1 = i;
 41             }else if(hT[i].weight < hT[s2].weight){
 42                 s2 = i;
 43             }
 44         }
 45     }
 46 }
 47 
 48 // 構造有n個權值(葉子節點)的哈夫曼樹 
 49 void CreateHufmanTree(HuffmanTree &hT)
 50 {
 51     int n, m;
 52     cin >> n;
 53     m = 2*n - 1;
 54 
 55     hT = new HTNode[m + 1];    // 0號節點不使用 
 56     for(int i = 1; i <= m; ++ i){
 57         hT[i].parent = hT[i].lChild = hT[i].rChild = 0;
 58     }
 59     for(int i = 1; i <= n; ++ i){
 60         cin >> hT[i].weight;    // 輸入權值 
 61     }
 62     hT[0].weight = m;    // 用0號節點保存節點數量 
 63 
 64     /****** 初始化完畢, 創建哈夫曼樹 ******/
 65     for(int i = n + 1; i <= m; ++ i){
 66         int s1, s2;
 67         SelectMin(hT, i, s1, s2);
 68 
 69         hT[s1].parent = hT[s2].parent = i;
 70         hT[i].lChild = s1; hT[i].rChild = s2;    // 作為新節點的孩子 
 71         hT[i].weight = hT[s1].weight + hT[s2].weight;    // 新節點為左右孩子節點權值之和 
 72     }
 73 }
 74 
 75 int HuffmanTreeWPL_(HuffmanTree hT, int i, int deepth)
 76 {
 77     if(hT[i].lChild == 0 && hT[i].rChild == 0){
 78         return hT[i].weight * deepth;
 79     }
 80     else{
 81         return HuffmanTreeWPL_(hT, hT[i].lChild, deepth + 1) + HuffmanTreeWPL_(hT, hT[i].rChild, deepth + 1);
 82     }
 83 }
 84 
 85 // 計算WPL(帶權路徑長度) 
 86 int HuffmanTreeWPL(HuffmanTree hT)
 87 {
 88     return HuffmanTreeWPL_(hT, hT[0].weight, 0);
 89 }
 90 
 91 // 銷毀哈夫曼樹 
 92 void DestoryHuffmanTree(HuffmanTree &hT)
 93 {
 94     delete[] hT;
 95     hT = NULL;
 96 }
 97 
 98 int main()
 99 {
100     HuffmanTree hT;
101     CreateHufmanTree(hT);
102     cout << "WPL = " << HuffmanTreeWPL(hT) << endl;
103     DestoryHuffmanTree(hT);
104     return 0;
105 }

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM