哈夫曼编码编译器实践报告

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

计算机软件基础

课程设计

报告

设计题目:哈夫曼编\译码器

专业信息工程(系统工程方向)

班级09系统1班

学生董健

学号***********

指导教师陈金辉

一、设计题目

设计题目一哈夫曼编\译码器

设计要求:

1.初始化,键盘输入字符集大小n,n个字符和n个权植,建立哈夫曼树。

2.编码,利用建好的huffman树生成huffman编码;

3.输出编码;

4.译码功能;

5.字符和频度如下:

字符空格A B C D E F G H I J K L M N O P Q

频度186 64 13 22 32 103 21 15 47 57 1 2 32 20 57 63 15 1

字符R S T U V W X Y Z

频度48 51 80 23 8 18 1 16

1.1 问题分析

构造哈夫曼树时,首先将由n各字符形成的n个叶子节点存放到数组HTNode 的前n个分量中,然后根据前面介绍的哈夫曼方法的基本思想,不断将两个小子树合并为一个较大的子树,每次构成的新子树,每次构成的新子树的根节点顺序放到HTNode数组中的前n个分量的后面。译码功能,假定电文中只使用A、B、C、D、E、F6种字符,若进行等长编码,它们分别需要3位二进制字符,可一次编码为000、001、010、011、100、101。

1.2 数据结构与算法设计

哈夫曼编\译码器的主要功能是先建立哈夫曼树,然后利用建好的哈夫曼树生成哈夫曼编码后进行译码。

在数据通信中,经常需要将传送的文字转换成由二进制字符0、1组成的二进制串,称之为编码。构造一棵哈夫曼树,规定哈夫曼树中的左分之代表0,右分支代表1,则从根节点到每个叶子节点所经过的路径分支组成的0和1的序列便为该节点对应字符的编码,称之为哈夫曼编码。

最简单的二进制编码方式是等长编码。若采用不等长编码,让出现频率高的字符具有较短的编码,让出现频率低的字符具有较长的编码,这样可能缩短传送电文的总长度。哈夫曼树课用于构造使电文的编码总长最短的编码方案。

哈夫曼树编\译码器流程图

1.3 核心代码

哈夫曼编\译码器程序的主要代码如下所示:

#include

#include //要用system函数要调用的头文件

#include //用getch()要调用的头文件

#include

#define N 50 //义用N表示50叶节点数

#define M 2*N-1 //用M表示节点总数当叶节点数位n时总节点数为2n-1 #define MAXSIZE 100

typedef struct

{

char data; //结点值

int weight; //权值

int parent; //双亲结点

int lchild; //左孩子结点

int rchild; //右孩子结点

}HTNode;

typedef struct

{

char cd[N]; //存放哈夫曼码

int start; //从start开始读cd中的哈夫曼码

}HCode;

void CreateHT(HTNode ht[],int n) //调用输入的数组ht[],和节点数n {

int i,k,lnode,rnode;

int min1,min2;

for (i=0;i<2*n-1;i++)

ht[i].parent=ht[i].lchild=ht[i].rchild=-1; //所有结点的相关域置初值-1 for (i=n;i<2*n-1;i++) //构造哈夫曼树

{

min1=min2=32767; //int的范围是-32768—32767

lnode=rnode=-1; //lnode和rnode记录最小权值的两个结点位置

for (k=0;k<=i-1;k++)

{

if (ht[k].parent==-1) //只在尚未构造二叉树的结点中查找

{

if (ht[k].weight

{

min2=min1;rnode=lnode;

min1=ht[k].weight;lnode=k;

}

else if (ht[k].weight

{

min2=ht[k].weight;rnode=k;

}

}

}

ht[lnode].parent=i;ht[rnode].parent=i; //两个最小节点的父节点是i

ht[i].weight=ht[lnode].weight+ht[rnode].weight; //两个最小节点的父节点权值为两个最小节点权值之和

ht[i].lchild=lnode;ht[i].rchild=rnode; //父节点的左节点和右节点}

}

void CreateHCode(HTNode ht[],HCode hcd[],int n)

{

int i,f,c;

HCode hc;

for (i=0;i

{

hc.start=n;c=i;

f=ht[i].parent;

while (f!=-1) //循序直到树根结点结束循环

{

if (ht[f].lchild==c) //处理左孩子结点

hc.cd[hc.start--]='0';

else //处理右孩子结点

hc.cd[hc.start--]='1';

c=f;f=ht[f].parent;

}

hc.start++; //start指向哈夫曼编码hc.cd[]中最开始字符

hcd[i]=hc;

}

}

void DispHCode(HTNode ht[],HCode hcd[],int n) //输出哈夫曼编码的列表

{

int i,k;

printf(" 输出哈夫曼编码:\n");

相关文档
最新文档