数据结构哈夫曼编码实验报告

合集下载

哈夫曼编码的实验报告

哈夫曼编码的实验报告

哈夫曼编码的实验报告哈夫曼编码的实验报告一、引言信息的传输和存储是现代社会中不可或缺的一部分。

然而,随着信息量的不断增加,如何高效地表示和压缩信息成为了一个重要的问题。

在这个实验报告中,我们将探讨哈夫曼编码这一种高效的信息压缩算法。

二、哈夫曼编码的原理哈夫曼编码是一种变长编码方式,通过将出现频率较高的字符用较短的编码表示,而将出现频率较低的字符用较长的编码表示,从而实现信息的压缩。

它的核心思想是利用统计特性,将出现频率较高的字符用较短的编码表示,从而减少整体编码长度。

三、实验过程1. 统计字符频率在实验中,我们首先需要统计待压缩的文本中各个字符的出现频率。

通过遍历文本,我们可以得到每个字符出现的次数。

2. 构建哈夫曼树根据字符频率,我们可以构建哈夫曼树。

哈夫曼树是一种特殊的二叉树,其中每个叶子节点代表一个字符,并且叶子节点的权值与字符的频率相关。

构建哈夫曼树的过程中,我们需要使用最小堆来选择权值最小的两个节点,并将它们合并为一个新的节点,直到最终构建出一棵完整的哈夫曼树。

3. 生成编码表通过遍历哈夫曼树,我们可以得到每个字符对应的编码。

在遍历过程中,我们记录下每个字符的路径,左边走为0,右边走为1,从而生成编码表。

4. 进行编码和解码在得到编码表后,我们可以将原始文本进行编码,将每个字符替换为对应的编码。

编码后的文本长度将会大大减少。

为了验证编码的正确性,我们还需要进行解码,将编码后的文本还原为原始文本。

四、实验结果我们选取了一段英文文本作为实验数据,并进行了哈夫曼编码。

经过编码后,原始文本长度从1000个字符减少到了500个字符。

解码后的文本与原始文本完全一致,验证了哈夫曼编码的正确性。

五、讨论与总结哈夫曼编码作为一种高效的信息压缩算法,具有广泛的应用前景。

通过将出现频率较高的字符用较短的编码表示,哈夫曼编码可以在一定程度上减小信息的存储和传输成本。

然而,哈夫曼编码也存在一些局限性,例如对于出现频率相近的字符,编码长度可能会相差较大。

数据结构哈夫曼编码实验报告

数据结构哈夫曼编码实验报告

数据结构实验报告――实验五简单哈夫曼编/译码的设计与实现本实验的目的是通过对简单哈夫曼编/译码系统的设计与实现来熟练掌握树型结构在实际问题中的应用。

此实验可以作为综合实验,阶段性实验时可以选择其中的几个功能来设计和实现。

一、【问题描述】利用哈夫曼编码进行通信可以大大提高信道利用率,缩短信息传输时间,降低传输成本。

但是,这要求在发送端通过一个编码系统对待传数据预先编码,在接收端将传来的数据进行译码,此实验即设计这样的一个简单编/码系统。

系统应该具有如下的几个功能:1、接收原始数据。

从终端读入字符集大小n,以及n个字符和n个权值,建立哈夫曼树,并将它存于文件中。

2、编码。

利用已建好的哈夫曼树(如不在内存,则从文件中读入),对文件中的正文进行编码,然后将结果存入文件中。

3、译码。

利用已建好的哈夫曼树将文件中的代码进行译码,结果存入文件中。

4、打印编码规则。

即字符与编码的一一对应关系。

二、【数据结构设计】1、构造哈夫曼树时使用静态链表作为哈夫曼树的存储。

在构造哈夫曼树时,设计一个结构体数组HuffNode保存哈夫曼树中各结点的信息,根据二叉树的性质可知,具有n个叶子结点的哈夫曼树共有2n-1个结点,所以数组HuffNode 的大小设置为2n-1,描述结点的数据类型为:typedef struct{int weight;eight=0;HaffNode[i].parent=-1;HaffNode[i].lchild=-1;HaffNode[i].rchild=-1;HaffNode[i].inf='0';}for(i=0;i<n;i++){cout<<"请输入字符"<<endl;cin>>HaffNode[i].inf;cout<<"请输入该字符的权值"<<endl;cin>>HaffNode[i].weight;}for(i=0;i<n-1;i++)arent==-1&&HaffNode[j].weight<m1){m2=m1;x2=x1;m1=HaffNode[j].weight;x1=j;}else{if(HaffNode[j].parent==-1&&HaffNode[j].weight<m2){m2=HaffNode[j].weight;x2=j;}}}arent=n+i;HaffNode[x2].parent=n+i;HaffNode[n+i].weight=HaffNode[x1].weight+HaffNode[x2].weight;HaffNode[n+i].lchild=x1;HaffNode[n+i].rchild=x2;HaffNode[n+i].inf=NULL;}cout<<"显示存储的哈弗曼树信息:"<<endl;cout<<"权值左孩子右孩子双亲"<<endl;for(i=0;i<2*n-1;i++){cout<<HaffNode[i].weight<<" ";cout<<HaffNode[i].lchild<<" ";cout<<HaffNode[i].rchild<<" ";cout<<HaffNode[i].parent<<" ";cout<<HaffNode[i].inf<<endl;}arent;while(p!=-1){if(HaffNode[p].lchild==c)[]=0;else[]=1;;c=p;p=HaffNode[c].parent;}for(j=+1;j<n;j++)HaffCode[i].bit[j]=[j];HaffCode[i].start=;}for(i=0;i<n;i++){outfile<<HaffNode[i].inf;for(j=HaffCode[i].start+1;j<n;j++)outfile<<HaffCode[i].bit[j];}cout<<"字符信息--编码信息"<<endl;for(i=0;i<n;i++){cout<<HaffNode[i].inf<<"---";for(j=HaffCode[i].start+1;j<n;j++)cout<<HaffCode[i].bit[j];cout<<endl;}();cout<<"请输入要编码的字符串,基本元素为(";for(i=0;i<n;i++)cout<<HaffNode[i].inf<<",";cout<<")"<<endl;char inf[100];cin>>inf;int f=strlen(inf);fstream outfile1;("E:\\",ios::out|ios::binary);nf){for(j=HaffCode[i].start+1;j<n;j++){((char*)&HaffCode[i].bit[j],sizeof(HaffCode[i].bit[j]));cout<<HaffCode[i].bit[j];}}}}}cout<<endl;cout<<"编译后的代码串已经存入文件中!"<<endl;cout<<endl;();delete []HaffNode;delete []HaffCode;}void decode( int &n)child!=-1&&HaffNode[m].rchild!=-1)if(tempcode[i]==0){m=HaffNode[m].lchild;i++;}else if(tempcode[i]==1){m=HaffNode[m].rchild;i++;}}cout<<HaffNode[m].inf;outfile<<HaffNode[m].inf;m=2*n-2;}cout<<endl;();cout<<"译码后的结果已经存入中!"<<endl;delete []HaffNode;}int main(){int n;cout<<"************* 欢迎进入编/译码系统!*********************"<<endl;int ch1;do{cout<<" 1.建树"<<endl;cout<<" 2:编码,并显示字符和对应的编码"<<endl;cout<<" 3:译码"<<endl;cout<<" 0:退出"<<endl;cout<<"********************************************************"<<end l;cout<<"请选择(0~3):";cin>>ch1;while(!(ch1<=3&&ch1>=0)) //输入不在0到4之间无效{cout<<"数据输入错误,请重新选择(0~4):";cin>>ch1;switch(ch1){case 1:{cout<<"\t\t\t请输入编码个数"<<endl;//叶子结点个数cin>>n;Creat_Haffmantree(n);break;}case 2: HaffCode(n); break;case 3: decode(n); break;}}while(ch1!=0);return 0;}五、【运行与测试】1、令叶子结点个数n为4,权值集合为{1,3,5,7},字符集合为{A,B,C,D},并有如下对应关系,A――1、B――3,C――5,D――7,调用初始化功能模块可以正确接收这些数据。

数据结构哈夫曼编码实验报告

数据结构哈夫曼编码实验报告

数据结构哈夫曼编码实验报告一、实验目的:通过哈夫曼编、译码算法的实现,巩固二叉树及哈夫曼树相关知识的理解掌握,训练学生运用所学知识,解决实际问题的能力。

二、实验内容:已知每一个字符出现的频率,构造哈夫曼树,并设计哈夫曼编码。

1、从终端读入字符集大小n,以及n个字符和n个权值,建立哈夫曼树。

2、打印每一个字符对应的哈夫曼编码。

3、对从终端读入的字符串进行编码,并显示编码结果。

4、对从终端读入的编码串进行译码,并显示译码结果。

三、实验方案设计:(对基本数据类型定义要有注释说明,解决问题的算法思想描述要完整,算法结构和程序功能模块之间的逻辑调用关系要清晰,关键算法要有相应的流程图,对算法的时间复杂度要进行分析)1、算法思想:(1)构造两个结构体分别存储结点的字符及权值、哈夫曼编码值:(2)读取前n个结点的字符及权值,建立哈夫曼树:(3)根据哈夫曼树求出哈夫曼编码:2、算法时间复杂度:(1)建立哈夫曼树时进行n到1次合并,产生n到1个新结点,并选出两个权值最小的根结点:O(n²);(2)根据哈夫曼树求出哈夫曼编码:O(n²)。

(3)读入电文,根据哈夫曼树译码:O(n)。

四、该程序的功能和运行结果:(至少有三种不同的测试数据和相应的运行结果,充分体现该程序的鲁棒性)1、输入字符A,B,C,D,E,F及其相应权值16、12、9、30、6、3。

2、输入字符F,E,N,G,H,U,I及其相应权值30、12、23、22、12、7、9。

3、输入字符A,B,C,D,E,F,G,H,I,G及其相应权值19、23、25、18、12、67、23、9、32、33。

数据结构哈夫曼编码实验报告

数据结构哈夫曼编码实验报告

数据结构哈夫曼编码实验报告数据结构哈夫曼编码实验报告1·实验目的1·1 理解哈夫曼编码的基本原理1·2 掌握哈夫曼编码的算法实现方式1·3 熟悉哈夫曼编码在数据压缩中的应用2·实验背景2·1 哈夫曼编码的概念和作用2·2 哈夫曼编码的原理和算法2·3 哈夫曼编码在数据压缩中的应用3·实验环境3·1 硬件环境:计算机、CPU、内存等3·2 软件环境:编程语言、编译器等4·实验过程4·1 构建哈夫曼树4·1·1 哈夫曼树的构建原理4·1·2 哈夫曼树的构建算法4·2 哈夫曼编码4·2·1 哈夫曼编码的原理4·2·2 哈夫曼编码的算法4·3 实现数据压缩4·3·1 数据压缩的概念和作用4·3·2 哈夫曼编码在数据压缩中的应用方法5·实验结果5·1 构建的哈夫曼树示例图5·2 哈夫曼编码表5·3 数据压缩前后的文件大小对比5·4 数据解压缩的正确性验证6·实验分析6·1 哈夫曼编码的优点和应用场景分析6·2 数据压缩效果的评估和对比分析6·3 实验中遇到的问题和解决方法7·实验总结7·1 实验所获得的成果和收获7·2 实验中存在的不足和改进方向7·3 实验对于数据结构学习的启示和意义附件列表:1·实验所用的源代码文件2·实验中用到的测试数据文件注释:1·哈夫曼编码:一种用于数据压缩的编码方法,根据字符出现频率构建树形结构,实现高频字符用较短编码表示,低频字符用较长编码表示。

2·哈夫曼树:由哈夫曼编码算法构建的一种特殊的二叉树,用于表示字符编码的结构。

数据结构 哈夫曼编码实验报告

数据结构 哈夫曼编码实验报告

数据结构哈夫曼编码实验报告数据结构哈夫曼编码实验报告1. 实验目的本实验旨在通过实践理解哈夫曼编码的原理和实现方法,加深对数据结构中树的理解,并掌握使用Python编写哈夫曼编码的能力。

2. 实验原理哈夫曼编码是一种用于无损数据压缩的算法,通过根据字符出现的频率构建一棵哈夫曼树,并根据哈夫曼树对应的编码。

根据哈夫曼树的特性,频率较低的字符具有较长的编码,而频率较高的字符具有较短的编码,从而实现了对数据的有效压缩。

实现哈夫曼编码的主要步骤如下:1. 统计输入文本中每个字符的频率。

2. 根据字符频率构建哈夫曼树,其中树的叶子节点代表字符,内部节点代表字符频率的累加。

3. 遍历哈夫曼树,根据左右子树的关系对应的哈夫曼编码。

4. 使用的哈夫曼编码对输入文本进行编码。

5. 将编码后的二进制数据保存到文件,同时保存用于解码的哈夫曼树结构。

6. 对编码后的文件进行解码,还原原始文本。

3. 实验过程3.1 统计字符频率首先,我们需要统计输入文本中每个字符出现的频率。

可以使用Python中的字典数据结构来记录字符频率。

遍历输入文本的每个字符,将字符添加到字典中,并递增相应字符频率的计数。

```pythondef count_frequency(text):frequency = {}for char in text:if char in frequency:frequency[char] += 1else:frequency[char] = 1return frequency```3.2 构建哈夫曼树根据字符频率构建哈夫曼树是哈夫曼编码的核心步骤。

我们可以使用最小堆(优先队列)来高效地构建哈夫曼树。

首先,将每个字符频率作为节点存储到最小堆中。

然后,从最小堆中取出频率最小的两个节点,将它们作为子树构建成一个新的节点,新节点的频率等于两个子节点频率的和。

将新节点重新插入最小堆,并重复该过程,直到最小堆中只剩下一个节点,即哈夫曼树的根节点。

数据结构课程设计哈夫曼编码实验

数据结构课程设计哈夫曼编码实验

数据结构设计性实验Huffman编码与译码学号姓名班级设计性实验—Huffman 编码与译码一.实验目的:在掌握相关基础知识的基础上,学会自己设计实验算法,熟练掌握Huffman 树的建立方法,Huffman 编码的方法,进而设计出Huffman 译码算法,并编程实现。

二.实验要求:在6学时以内,制作出能够实现基于26个英文字母的任意字符串的编译码。

写出技术工作报告并附源程序。

三.实验内容及任务:1.设字符集为26个英文字母,其出现频度如下表所示。

2.建Huffman 树; 3.利用所建Huffman 树对任一字符串文件进行编码——即设计一个Huffman 编码器;4.对任一字符串文件的编码进行译码——即设计一个Huffman 译码器。

实现步骤:1.数据存储结构设计; 2.操作模块设计; 3.建树算法设计; 4.编码器设计;5. 译码器设计;51 48 1 15 63 57 20 32 5 1频度z y x w v u t 字符11611882380频度p 21 f q15 g r 47 h s o n m l k j 字符 57 103 32 22 13 64 186 频度 i e d c b a 空格 字符四.分析以及算法描述1.分析问题1)首先学习二叉树的知识,了解二叉树的路径、权数以及带权路径长度计算。

2)认识霍夫曼树,了解霍夫曼树的定义,构造霍夫曼树构造算法①又给定的n个权值{w1,w2,w3,……,w n}构造根节点的二叉树,从而得到一个二叉树森林F={T1,T2,T3,……T n}。

②在二叉树森里选取根节点全职最小和此最小的两棵二叉树作为左右节点构造新的二叉树,此时新的二叉树的根节点权值为左右子树权值之和。

③在二叉树森林中删除作为新二叉树的根节点左右子树的两棵二叉树,将新的二叉树加入到二叉树森林F中。

④重复②和③,当二叉树森林F只剩下一棵二叉树时,这棵二叉树是所构造的霍夫曼树。

3)练习通过普通树来构造霍夫曼树。

哈夫曼树编码实验报告

哈夫曼树编码实验报告

哈夫曼树编码实验报告哈夫曼树编码实验报告引言:哈夫曼树编码是一种常用的数据压缩算法,通过对数据进行编码和解码,可以有效地减小数据的存储空间。

本次实验旨在探究哈夫曼树编码的原理和应用,并通过实际案例验证其有效性。

一、哈夫曼树编码原理哈夫曼树编码是一种变长编码方式,根据字符出现的频率来确定不同字符的编码长度。

频率较高的字符编码较短,频率较低的字符编码较长,以达到最佳的数据压缩效果。

1.1 字符频率统计首先,需要对待编码的数据进行字符频率统计。

通过扫描数据,记录每个字符出现的次数,得到字符频率。

1.2 构建哈夫曼树根据字符频率构建哈夫曼树,频率较低的字符作为叶子节点,频率较高的字符作为父节点。

构建哈夫曼树的过程中,需要使用最小堆来维护节点的顺序。

1.3 生成编码表通过遍历哈夫曼树,从根节点到每个叶子节点的路径上的左右分支分别赋予0和1,生成对应的编码表。

1.4 数据编码根据生成的编码表,将待编码的数据进行替换,将每个字符替换为对应的编码。

编码后的数据长度通常会减小,实现了数据的压缩。

1.5 数据解码利用生成的编码表,将编码后的数据进行解码,恢复原始数据。

二、实验过程与结果为了验证哈夫曼树编码的有效性,我们选择了一段文本作为实验数据,并进行了以下步骤:2.1 字符频率统计通过扫描文本,统计每个字符出现的频率。

我们得到了一个字符频率表,其中包含了文本中出现的字符及其对应的频率。

2.2 构建哈夫曼树根据字符频率表,我们使用最小堆构建了哈夫曼树。

频率较低的字符作为叶子节点,频率较高的字符作为父节点。

最终得到了一棵哈夫曼树。

2.3 生成编码表通过遍历哈夫曼树,我们生成了对应的编码表。

编码表中包含了每个字符的编码,用0和1表示。

2.4 数据编码将待编码的文本数据进行替换,将每个字符替换为对应的编码。

编码后的数据长度明显减小,实现了数据的压缩。

2.5 数据解码利用生成的编码表,将编码后的数据进行解码,恢复原始文本数据。

数据结构哈夫曼编码实验报告

数据结构哈夫曼编码实验报告

数据结构哈夫曼编码实验报告【正文】1.实验目的本实验旨在研究哈夫曼编码的原理和实现方法,通过实验验证哈夫曼编码在数据压缩中的有效性,并分析其应用场景和优缺点。

2.实验原理2.1 哈夫曼编码哈夫曼编码是一种无损数据压缩算法,通过根据字符出现的频率构建一颗哈夫曼树,将频率较高的字符用较短的编码表示,频率较低的字符用较长的编码表示。

哈夫曼编码的编码表是唯一的,且能够实现前缀编码,即一个编码不是另一个编码的前缀。

2.2 构建哈夫曼树构建哈夫曼树的过程如下:1) 将每个字符及其频率作为一个节点,构建一个节点集合。

2) 每次从节点集合中选择出现频率最低的两个节点,构建一个新节点,并将这两个节点从集合中删除。

3) 将新节点加入节点集合。

4) 重复以上步骤,直到节点集合中只有一个节点,这个节点就是哈夫曼树的根节点。

2.3 编码过程根据哈夫曼树,对每个字符进行编码:1) 从根节点开始,根据左子树为0,右子树为1的规则,将编码依次加入编码表。

2) 对于每个字符,根据编码表获取其编码。

3) 将编码存储起来,得到最终的编码序列。

3.实验步骤3.1 数据读取与统计从输入文件中读取字符序列,并统计各个字符的频率。

3.2 构建哈夫曼树根据字符频率构建哈夫曼树。

3.3 构建编码表根据哈夫曼树,构建每个字符的编码表。

3.4 进行编码根据编码表,对输入的字符序列进行编码。

3.5 进行解码根据哈夫曼树,对编码后的序列进行解码。

4.实验结果与分析4.1 压缩率分析计算原始数据和压缩后数据的比值,分析压缩率。

4.2 编码效率分析测试编码过程所需时间,分析编码效率。

4.3 解码效率分析测试解码过程所需时间,分析解码效率。

4.4 应用场景分析分析哈夫曼编码在实际应用中的优势和适用场景。

5.结论通过本次实验,我们深入了解了哈夫曼编码的原理和实现方法,实践了哈夫曼编码的过程,并对其在数据压缩中的有效性进行了验证。

实验结果表明,哈夫曼编码能够实现较高的压缩率和较高的编解码效率。

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

数据结构实验报告――实验五简单哈夫曼编/译码的设计与实现本实验的目的是通过对简单哈夫曼编/译码系统的设计与实现来熟练掌握树型结构在实际问题中的应用。

此实验可以作为综合实验,阶段性实验时可以选择其中的几个功能来设计和实现。

一、【问题描述】利用哈夫曼编码进行通信可以大大提高信道利用率,缩短信息传输时间,降低传输成本。

但是,这要求在发送端通过一个编码系统对待传数据预先编码,在接收端将传来的数据进行译码,此实验即设计这样的一个简单编/码系统。

系统应该具有如下的几个功能:1、接收原始数据。

从终端读入字符集大小n,以及n个字符和n个权值,建立哈夫曼树,并将它存于文件nodedata.dat中。

2、编码。

利用已建好的哈夫曼树(如不在存,则从文件nodedata.dat中读入),对文件中的正文进行编码,然后将结果存入文件code.dat中。

3、译码。

利用已建好的哈夫曼树将文件code.dat中的代码进行译码,结果存入文件textfile.dat中。

4、打印编码规则。

即字符与编码的一一对应关系。

二、【数据结构设计】1、构造哈夫曼树时使用静态链表作为哈夫曼树的存储。

在构造哈夫曼树时,设计一个结构体数组HuffNode保存哈夫曼树中各结点的信息,根据二叉树的性质可知,具有n个叶子结点的哈夫曼树共有2n-1个结点,所以数组HuffNode的大小设置为2n-1,描述结点的数据类型为:typedef struct{int weight;//结点权值int parent;int lchild;int rchild;char inf;}HNodeType;2、求哈夫曼编码时使用一维结构数组HuffCode作为哈夫曼编码信息的存储。

求哈夫曼编码,实质上就是在已建立的哈夫曼树中,从叶子结点开始,沿结点的双亲链域回退到根结点,没回退一步,就走过了哈夫曼树的一个分支,从而得到一位哈夫曼码值,由于一个字符的哈夫曼编码是从根结点到相应叶子结点所经过的路径上各分支所组成的0、1序列,因此先得到的分支代码为所求编码的低位码,后得到的分支代码位所求编码的高位码,所以设计如下数据类型:#define MAXBIT 10typedef struct{int bit[MAXBIT];int start;}HcodeType;3、文件nodedata.dat、code.dat和textfile.dat。

三、【功能(函数)设计】1、初始化功能模块。

此功能模块的功能为从键盘接收字符集大小n,以及n个字符和n个权值。

2、建立哈夫曼树的功能模块。

此模块功能为使用1中得到的数据按照教材中的构造哈夫曼树的算法构造哈夫曼树,即将HuffNode数组中的各个位置的各个域都添上相关的值,并将这个结构体数组存于文件hfmtree.dat中。

3、建立哈夫曼编码的功能模块。

此模块功能为从文件nodedata.dat中读入相关的字符信息进行哈夫曼编码,然后将结果存入code.dat中,同时将字符与0、1代码串的一一对应关系打印到屏幕上。

4、译码的功能模块。

此模块功能为接收需要译码的0、1代码串,按照3中建立的编码规则将其翻译成字符集中字符所组成的字符串形式,存入文件textfile.dat,同时将翻译的结果在屏幕上打印输出。

四、【编码实现】#include<iostream.h>#include<fstream.h>#include<string.h>#include<stdlib.h>#define MaxBit 10#define Maxvalue 100//应该大于权重之和#define Maxleaf 100#define Maxnode Maxleaf*2-1typedef struct{int weight;int parent;int lchild;int rchild;char inf;}HNodeType;struct HcodeType{int bit[MaxBit];int start;};void Creat_Haffmantree(int &n){HNodeType *HaffNode=new HNodeType[2*n-1];int i,j;int m1,m2,x1,x2;for(i=0;i<2*n-1;i++){HaffNode[i].weight=0;HaffNode[i].parent=-1;HaffNode[i].lchild=-1;HaffNode[i].rchild=-1;HaffNode[i].inf='0';}for(i=0;i<n;i++){cout<<"请输入字符"<<endl;cin>>HaffNode[i].inf;cout<<"请输入该字符的权值"<<endl;cin>>HaffNode[i].weight;}for(i=0;i<n-1;i++)//构造哈夫曼树{m1=m2=Maxvalue;x1=x2=0;for(j=0;j<n+i;j++)//选取最小和次小{if(HaffNode[j].parent==-1&&HaffNode[j].weight<m1){m2=m1;x2=x1;m1=HaffNode[j].weight;x1=j;}else{if(HaffNode[j].parent==-1&&HaffNode[j].weight<m2){m2=HaffNode[j].weight;x2=j;}}}//将找出的最小和次小合并,创造其父母结点HaffNode[x1].parent=n+i;HaffNode[x2].parent=n+i;HaffNode[n+i].weight=HaffNode[x1].weight+HaffNode[x2].weight;HaffNode[n+i].lchild=x1;HaffNode[n+i].rchild=x2;HaffNode[n+i].inf=NULL;}cout<<"显示存储的哈弗曼树信息:"<<endl;cout<<"权值左孩子右孩子双亲"<<endl;for(i=0;i<2*n-1;i++){cout<<HaffNode[i].weight<<" ";cout<<HaffNode[i].lchild<<" ";cout<<HaffNode[i].rchild<<" ";cout<<HaffNode[i].parent<<" ";cout<<HaffNode[i].inf<<endl;}//写入文件fstream outfile1;outfile1.open("E:\\nodedata.dat",ios::out|ios::trunc|ios::binary);//建立进行写入的文件if(!outfile1) //没有创建成功则显示相应信息{cout<<"nodedata.dat文件不能打开"<<endl;abort();}for(i=0;i<2*n-1;i++) //将存中从HaffNode[i]地址开始的sizeof(HaffNode[i])的容写入文件中outfile1.write((char*)&HaffNode[i],sizeof(HaffNode[i]));outfile1.close ();//关闭文件delete []HaffNode;}void HaffCode(int &n)//哈夫曼编码{HNodeType *HaffNode=new HNodeType[Maxnode];HcodeType *HaffCode=new HcodeType[Maxleaf];HcodeType cd;int i,j,c,p;fstream in("E:\\nodedata.dat",ios::in|ios::binary);in.read((char*)HaffNode,(2*n-1)*sizeof(HNodeType));in.close();fstream outfile;outfile.open("E:\\codedata.dat",ios::out|ios::binary);//建立进行写入的文件for(i=0;i<n;i++){cd.start=n-1;c=i;p=HaffNode[c].parent;while(p!=-1){if(HaffNode[p].lchild==c)cd.bit[cd.start]=0;elsecd.bit[cd.start]=1;cd.start--;c=p;p=HaffNode[c].parent;}for(j=cd.start+1;j<n;j++)HaffCode[i].bit[j]=cd.bit[j];HaffCode[i].start=cd.start;}for(i=0;i<n;i++){outfile<<HaffNode[i].inf;for(j=HaffCode[i].start+1;j<n;j++) outfile<<HaffCode[i].bit[j];}cout<<"字符信息--编码信息"<<endl; for(i=0;i<n;i++){cout<<HaffNode[i].inf<<"---";for(j=HaffCode[i].start+1;j<n;j++)cout<<HaffCode[i].bit[j];cout<<endl;}outfile.close ();cout<<"请输入要编码的字符串,基本元素为(";for(i=0;i<n;i++)cout<<HaffNode[i].inf<<",";cout<<")"<<endl;char inf[100];cin>>inf;int f=strlen(inf);fstream outfile1;outfile1.open("E:\\code.dat",ios::out|ios::binary);//建立进行写入的文件if(!outfile1){cout<<"code.dat文件不能打开!"<<endl;abort();}else{ cout<<endl;cout<<"字符串编码后为:";for(int x=0;x<f;x++){for(i=0;i<n;i++){if(inf[x]==HaffNode[i].inf){for(j=HaffCode[i].start+1;j<n;j++){outfile1.write((char*)&HaffCode[i].bit[j],sizeof(HaffCode[i].bit[j]));cout<<HaffCode[i].bit[j];}}}}}cout<<endl;cout<<"编译后的代码串已经存入code.dat文件中!"<<endl;cout<<endl;outfile1.close();delete []HaffNode;delete []HaffCode;}void decode( int &n)//解码{int i;HNodeType *HaffNode=new HNodeType[2*n-1];fstream infile1;infile1.open("E:\\nodedata.dat",ios::in|ios::binary);//读出哈夫曼树if(!infile1){cout<<"nodedata.dat文件不能打开"<<endl;abort();}for(i=0;i<2*n-1;i++)infile1.read((char*)&HaffNode[i],sizeof(HNodeType));infile1.close();int tempcode[100];int num=0;for(i=0;i<100;i++)tempcode[i]=-1;HcodeType *Code=new HcodeType[n];fstream infile2;//读编码infile2.open("E:\\code.dat",ios::in|ios::binary);while(!infile2.eof()){infile2.read((char*)&tempcode[num],sizeof(tempcode[num]));num++;}infile2.close();num--;cout<<"从文件中读出的编码为"<<endl;for(i=0;i<num;i++)cout<<tempcode[i];cout<<endl;int m=2*n-2;i=0;cout<<endl;cout<<"译码后为:"<<endl;fstream outfile;outfile.open("E:\\textfile.txt",ios::out);if(!outfile){cout<<"textfile.txt文件不能打开!"<<endl;abort();}while(i<num)// 小于字符串的长度{while(HaffNode[m].lchild!=-1&&HaffNode[m].rchild!=-1) {if(tempcode[i]==0){m=HaffNode[m].lchild;i++;}else if(tempcode[i]==1){m=HaffNode[m].rchild;i++;}}cout<<HaffNode[m].inf;outfile<<HaffNode[m].inf;m=2*n-2;}cout<<endl;outfile.close();cout<<"译码后的结果已经存入textfile.txt中!"<<endl;delete []HaffNode;}int main(){int n;cout<<"************* 欢迎进入编/译码系统!*********************"<<endl;int ch1;do{cout<<" 1.建树"<<endl;cout<<" 2:编码,并显示字符和对应的编码"<<endl;cout<<" 3:译码"<<endl;cout<<" 0:退出"<<endl;cout<<"********************************************************"<<endl;cout<<"请选择(0~3):";cin>>ch1;while(!(ch1<=3&&ch1>=0)) //输入不在0到4之间无效{cout<<"数据输入错误,请重新选择(0~4):";cin>>ch1;}switch(ch1){case 1:{cout<<"\t\t\t请输入编码个数"<<endl;//叶子结点个数cin>>n;Creat_Haffmantree(n);break;}case 2: HaffCode(n); break;case 3: decode(n); break;}}while(ch1!=0);return 0;}五、【运行与测试】1、令叶子结点个数n为4,权值集合为{1,3,5,7},字符集合为{A,B,C,D},并有如下对应关系,A――1、B――3,C――5,D――7,调用初始化功能模块可以正确接收这些数据。

相关文档
最新文档