哈夫曼二叉樹原始碼 (轉)
哈夫曼二叉樹原始碼:
給定一個字串,根據統計字串中各個字元出現的頻率對字元進行哈夫曼編碼,然後對原字串進行編碼,並輸出編碼後的內容
——資料結構
#include
#define MAX_NODE 1024
#define MAX_WEIGHT 4096
typedef struct HaffmanTreeNode {
char ch, code[15];
int weight;
int parent, lchild, rchild;
} HTNode, *HaTree;
typedef struct {
HTNode arr[MAX_NODE];
int total;
} HTree;
/* 統計字元出現的頻率 */
int statistic_char(char *text, HTree *t){
int i, j;
int text_len = strlen(text);
t->total = 0;
for (i=0; i for (j=0; j t->arr[j].weight ++; break; } if (j==t->total) { t->arr[t->total].ch = text[i]; t->arr[t->total].weight = 1; t->total ++; } } printf("char frequence
"); for (i=0; i printf("'%c' %d
", t->arr[i].ch, t->arr[i].weight); printf("
"); return t->total; } int create_htree(HTree *t) { int i; int total_node = t->total * 2 - 1; int min1, min2; /* 權最小的兩個結點 */ int min1_i, min2_i; /* 權最小結點對應的編號 */ int leaves = t->total; for (i=0; i t->arr[i].parent = -1; t->arr[i].rchild = -1; t->arr[i].lchild = -1; } while (t->total < total_node) { min1 = min2 = MAX_WEIGHT; for (i=0; i if (t->arr[i].parent == -1 /* 結點沒有被合併 */ && t->arr[i].weight < min2) { /* 結點的權比最小權小 */ if (t->arr[i].weight < min1) { /* 如果它比最小的結點還小 */ min2_i = min1_i; min2 = min1; min1_i = i; min1 = t->arr[i].weight; } else { min2_i = i; min2 = t->arr[i].weight; } } } t->arr[t->total].weight = min1 + min2; t->arr[t->total].parent = -1; t->arr[t->total].lchild = min1_i; t->arr[t->total].rchild = min2_i; t->arr[min1_i].parent = t->total; t->arr[min2_i].parent = t->total; t->arr[t->total].ch = ' '; t->total ++; } return 0; } /* 對哈夫曼樹進行編碼 */ void coding(HTree *t, int head_i, char *code) { if ( head_i == -1) return; if (t->arr[head_i].lchild == -1 && t->arr[head_i].rchild == -1) { strcpy(t->arr[head_i].code, code); printf("'%c': %s
", t->arr[head_i].ch, t->arr[head_i].code); } else { int len = strlen(code); strcat(code, "0"); coding(t, t->arr[head_i].lchild, code); code[len] = '1'; coding(t, t->arr[head_i].rchild, code); code[len] = ''; } } /* 中序列印樹 */ void print_htree_ldr(HTree *t, int head_i, int deep, int* path) { int i; if (head_i == -1) return; path[deep] = 0; print_htree_ldr(t, t->arr[head_i].lchild, deep + 1, path); if (deep) printf(" "); for (i=1; i int dir = path[i]==path[i-1]; if ( t->arr[head_i].lchild == -1 && t->arr[head_i].rchild == -1) printf("%s── %d '%c'
", dir? "┌":"└", t->arr[head_i].weight, t->arr[head_i].ch); else if (head_i != t->total-1) printf("%s─%02d┤
", dir? "┌":"└"", t->arr[head_i].weight); else printf(" %02d┤
", t->arr[head_i].weight); path[deep] = 1; print_htree_ldr(t, t->arr[head_i].rchild, deep + 1, path); } /* 對字元進行編碼 */ void code_string(char *text, HTree *t) { int i, j, text_len = strlen(text); int n = 0; for (i=0; i char ch = text[i]; for (j=0; j printf("%s ", t->arr[j].code); n += strlen(t->arr[j].code); break; } } printf("
%d chars, Total len = %d
", text_len, n); } int main(int argc, char* argv[]) { HTree t; char text[128]="ABAAAAEEEAAACCCCAAAACCDEA"; char code[128] = ""; int path[16]={0}; statistic_char(text, &t); create_htree(&t); print_htree_ldr(&t, t.total-1, 0, path); coding(&t, t.total-1, code); code_string(text, &t); return 0; } 輸出結果: char frequence ┌── 6 'C'
'A' 13
'B' 1
'E' 4
'C' 6
'D' 1
┌─12┤
│ │ ┌── 1 'B'
│ │ ┌─02┤
│ │ │ └── 1 'D'
│ └─06┤
│ └── 4 'E'
25┤
└── 13 'A'
'C': 00
'B': 0100
'D': 0101
'E': 011
'A': 1
1 0100 1 1 1 1 011 011 011 1 1 1 00 00 00 00 1 1 1 1 00 00 0101 011 1
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/10752019/viewspace-957517/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- 哈夫曼樹
- 哈夫曼樹及其編碼
- Java 樹結構實際應用 二(哈夫曼樹和哈夫曼編碼)Java
- 最優二叉樹(哈夫曼樹)Java實現二叉樹Java
- 哈夫曼編碼
- 資料結構與演算法——赫夫曼樹(哈夫曼樹)資料結構演算法
- 6.6 哈夫曼樹及其應用
- 哈夫曼樹學習筆記筆記
- 【資料結構X.11】程式碼實現 哈夫曼樹的建立,建立,構造,實現哈夫曼編碼資料結構
- Task A2 哈夫曼樹的應用
- 資料結構-哈夫曼樹(python實現)資料結構Python
- 重學資料結構之哈夫曼樹資料結構
- 哈夫曼樹及其應用(檔案壓縮)
- 資料結構與演算法:哈夫曼樹資料結構演算法
- 一本正經的聊資料結構(6):最優二叉樹 —— 哈夫曼樹資料結構二叉樹
- 哈夫曼編碼 —— Lisp 與 Python 實現LispPython
- 高階資料結構---赫(哈)夫曼樹及java程式碼實現資料結構Java
- 小任的第一篇部落格-哈夫曼樹
- 【資料結構】哈夫曼樹的建立與基礎應用資料結構
- 有趣的赫夫曼樹
- 從哈夫曼編碼中我們學到了什麼?
- 曼哈頓距離與切比雪夫距離
- 資料結構之哈弗曼樹資料結構
- C#資料結構-赫夫曼樹C#資料結構
- 哈夫曼實現檔案壓縮解壓縮(c語言)C語言
- 曼哈頓距離與切比雪夫距離的互化
- 玩轉二叉樹二叉樹
- 玩轉二叉樹(樹的遍歷)二叉樹
- 程式碼隨想錄day14 || 226 翻轉二叉樹,101 對稱二叉樹, 104 二叉樹的最大深度, 111 二叉樹的最小深度二叉樹
- JavaScript 二叉搜尋樹以及實現翻轉二叉樹JavaScript二叉樹
- 二叉樹和森林轉換二叉樹
- 平衡二叉樹(AVL樹)和 二叉排序樹轉化為平衡二叉樹 及C語言實現二叉樹排序C語言
- 原始碼原始碼原始碼樹品原始碼原始碼
- iOS實現反轉二叉樹iOS二叉樹
- 程式碼隨想錄——二叉樹-12.平衡二叉樹二叉樹
- 滿二叉樹、完全二叉樹、平衡二叉樹、二叉搜尋樹(二叉查詢樹)和最優二叉樹二叉樹
- [資料結構] 樹、二叉樹、森林的轉換資料結構二叉樹
- 二叉樹翻轉(分治思想的典型)二叉樹
- L2-011 玩轉二叉樹二叉樹