博客
关于我
哈弗曼编码
阅读量:364 次
发布时间:2019-03-04

本文共 5499 字,大约阅读时间需要 18 分钟。

数据压缩中的编码问题实验

#define _CRT_SECURE_NO_WARNINGS#include
#include
#define Minweight -1typedef struct Node* ElementType;struct Node { int Weight; char Key;};typedef struct HfTNode* HuffmanTree;struct HfTNode { ElementType Data; HuffmanTree Left, Right;};typedef struct Heapstruct* MinHeap;struct Heapstruct { HuffmanTree* Elements; int Size; int Capacity;};typedef struct SNode* PtrToSNode;struct SNode { ElementType Data; PtrToSNode Next; };typedef PtrToSNode Stack;Stack CreateStack(void);//创建一个栈int IsEmpty_Stack(Stack);//判断栈是否为空void Push(Stack, ElementType);//将元素放入栈中ElementType Pop(Stack);//将元素从栈顶拿出ElementType GetStackTop(Stack);//查看栈顶元素MinHeap CreateMinHeap(int MaxSize);int IsEmpty_MinHeap(MinHeap H);int IsFull_MinHeap(MinHeap H);void Insert_MinHeap(MinHeap H, HuffmanTree Item);HuffmanTree Delete_MinHeap(MinHeap H);void MinMaking(MinHeap H, int Root);void BuildMinHeap(MinHeap H);HuffmanTree Huffman(MinHeap H);void PrintPath(HuffmanTree T);int main(void){ Stack S; int MaxSize; MinHeap H; HuffmanTree T; S = CreateStack(); do { printf("输入关键字个数\n"); scanf("%d", &MaxSize); getchar(); if (MaxSize <= 1) printf("不必为%d个关键字编码\n"); else break; } while (1); H = CreateMinHeap(MaxSize); for (int i = 1; i <= MaxSize; i++) { H->Elements[i] = (HuffmanTree)malloc(sizeof(struct HfTNode)); H->Elements[i]->Left = NULL; H->Elements[i]->Right = NULL; H->Elements[i]->Data = (ElementType)malloc(sizeof(struct HfTNode)); printf("输入关键字及出现频率\n"); scanf("%c %d", &H->Elements[i]->Data->Key, &H->Elements[i]->Data->Weight); getchar(); }//建立一个任意顺序存放关键字和权重的数组 T = Huffman(H);//将这个数组转换成哈弗曼树 printf("#######
#######\n"); PrintPath(T);//将哈弗曼树转换成编码!}//将哈弗曼树转换成编码void PrintPath(HuffmanTree T)//所有无用树结点的Key都会被修改为-1{ HuffmanTree PtoT; HuffmanTree Root; char Word[10]; int i = 0; while (T->Data->Key != -1) { PtoT = T; Root = PtoT; i = 0; while (1) { if (!PtoT->Left && !PtoT->Right) { Word[i++] = PtoT->Data->Key; Word[i] = '\0'; printf("%s\n", Word); PtoT->Data->Key = -1; if ((!Root->Left || Root->Left->Data->Key == -1) && (!Root->Right || Root->Right->Data->Key == -1)) Root->Data->Key = -1; break; } else if (PtoT->Left && PtoT->Left->Data->Key != -1) { Word[i++] = '1'; Root = PtoT; PtoT = PtoT->Left; continue; } else if (PtoT->Right && PtoT->Right->Data->Key != -1) { Word[i++] = '0'; Root = PtoT; PtoT = PtoT->Right; continue; } PtoT->Data->Key = -1; break; } }}//以下为用到的堆函数MinHeap CreateMinHeap(int MaxSize){ MinHeap H; H = (MinHeap)malloc(sizeof(struct Heapstruct)); H->Elements = (HuffmanTree*)malloc(sizeof(HuffmanTree) * (MaxSize + 1)); H->Size = MaxSize; H->Capacity = MaxSize; H->Elements[0] = (HuffmanTree)malloc(sizeof(struct HfTNode)); H->Elements[0]->Data = (ElementType)malloc(sizeof(struct Node)); H->Elements[0]->Data->Weight = Minwight; return H;}int IsEmpty_MinHeap(MinHeap H){ return (H->Size == 0);}int IsFull_MinHeap(MinHeap H){ return (H->Size == H->Capacity);}void Insert_MinHeap(MinHeap H, HuffmanTree Item){ int i; if (IsFull_MinHeap(H)) return; i = ++H->Size;//i相当于子结点下标,i/2相当于父结点下标 for (; H->Elements[i / 2]->Data->Weight > Item->Data->Weight; i /= 2) H->Elements[i] = H->Elements[i / 2]; H->Elements[i] = Item;}HuffmanTree Delete_MinHeap(MinHeap H){ HuffmanTree Item, MinItem; int Parent, Child; if (IsEmpty_MinHeap(H)) return NULL; MinItem = H->Elements[1]; Item = H->Elements[H->Size--]; for (Parent = 1; Parent * 2 <= H->Size; Parent = Child) { Child = Parent * 2; if (H->Elements[Child]->Data->Weight > H->Elements[Child + 1]->Data->Weight) Child++; if (H->Elements[Child]->Data->Weight > Item->Data->Weight) break; else H->Elements[Parent] = H->Elements[Child]; } H->Elements[Parent] = Item; return MinItem;}void MinMaking(MinHeap H, int Root){ int Parent, Child; HuffmanTree Item; Item = H->Elements[Root]; for (Parent = Root; Parent * 2 <= H->Size; Parent = Child) { Child = Parent * 2; if (Child + 1 < H->Size && H->Elements[Child]->Data->Weight > H->Elements[Child + 1]->Data->Weight) Child++; if (H->Elements[Child]->Data->Weight > Item->Data->Weight) break; else H->Elements[Parent] = H->Elements[Child]; } H->Elements[Parent] = Item;}void BuildMinHeap(MinHeap H){ int i; for (i = H->Size / 2; i >= 1; i--) { MinMaking(H, i); }}HuffmanTree Huffman(MinHeap H){ HuffmanTree T; BuildMinHeap(H); while (H->Size > 1) { T = (HuffmanTree)malloc(sizeof(struct HfTNode)); T->Left = Delete_MinHeap(H); T->Right = Delete_MinHeap(H); T->Data = (ElementType)malloc(sizeof(struct Node)); T->Data->Weight = T->Left->Data->Weight + T->Right->Data->Weight; Insert_MinHeap(H, T);//将新T插入最小值 } T = Delete_MinHeap(H); return T;}//以下为所用到的栈函数Stack CreateStack(void){ Stack S = (Stack)malloc(sizeof(struct SNode)); S->Next = NULL; return S;}int IsEmpty_Stack(Stack S){ return (S->Next == NULL);}void Push(Stack S, ElementType Sdata){ PtrToSNode P; P = (PtrToSNode)malloc(sizeof(struct SNode));//创建新的栈结点 P->Data = Sdata; P->Next = S->Next;//将栈顶链接在新栈顶后 S->Next = P;//将新栈顶链接在栈头后}ElementType Pop(Stack S){ if (IsEmpty_Stack(S)) { printf("The Stack is Empty."); return NULL; } else { PtrToSNode P; ElementType Sdata; P = S->Next;//找到栈顶结点 Sdata = P->Data;//取出数据 S->Next = P->Next;//栈头链接新的栈顶 free(P);//释放原栈顶 return Sdata; }}ElementType GetStackTop(Stack S){ if (IsEmpty_Stack(S)) { printf("The Stack is empty."); return NULL; } else return S->Next->Data;}

运行截图

转载地址:http://ivbr.baihongyu.com/

你可能感兴趣的文章
Mysql 脏页 脏读 脏数据
查看>>
mysql 自增id和UUID做主键性能分析,及最优方案
查看>>
Mysql 自定义函数
查看>>
mysql 行转列 列转行
查看>>
Mysql 表分区
查看>>
mysql 表的操作
查看>>
mysql 视图,视图更新删除
查看>>
MySQL 触发器
查看>>
mysql 让所有IP访问数据库
查看>>
mysql 记录的增删改查
查看>>
MySQL 设置数据库的隔离级别
查看>>
MySQL 证明为什么用limit时,offset很大会影响性能
查看>>
Mysql 语句操作索引SQL语句
查看>>
MySQL 误操作后数据恢复(update,delete忘加where条件)
查看>>
MySQL 调优/优化的 101 个建议!
查看>>
mysql 转义字符用法_MySql 转义字符的使用说明
查看>>
mysql 输入密码秒退
查看>>
mysql 递归查找父节点_MySQL递归查询树状表的子节点、父节点具体实现
查看>>
mysql 通过查看mysql 配置参数、状态来优化你的mysql
查看>>
mysql 里对root及普通用户赋权及更改密码的一些命令
查看>>