`
Touch_2011
  • 浏览: 292095 次
  • 性别: Icon_minigender_1
  • 来自: 武汉
社区版块
存档分类
最新评论

哈夫曼编码与解码(C语言实现)

阅读更多
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<conio.h>

#define MAXNUM 60

typedef struct
{
	char ch;
	int weight; //权值,这个字符出现的频率
	int parent;
	int left;
	int right;
}HuffNode;

typedef struct
{
	char code[MAXNUM];
	int start;
}HuffCode;

HuffNode ht[MAXNUM*2]; //存放哈夫曼树

HuffCode hcd[MAXNUM];  //存放ht数组中对应的字符的编码

int n;                 //字符的个数

//初始化哈夫曼树ht
void initHt()
{
	FILE * fp;
	char ch;
	int i=0;
	//从文件document/character.txt中读出要编码的字符和权值
	if((fp=fopen("document/character.txt","r"))==NULL){
		printf("can not open the file character.txt");
		exit(0);
	}
	ht[i].left=ht[i].right=ht[i].parent=-1;
	while((ch=fgetc(fp))!=EOF){
		if(ch=='\n'){
			i++;
			ht[i].left=ht[i].right=ht[i].parent=-1;		
		}
		else if((ch>='a' && ch<='z')||(ch>='A' && ch<='Z'))
			ht[i].ch=ch;
		else if(ch>='0'&&ch<='9')
			ht[i].weight=ht[i].weight*10+ch-'0';
	}
	n=i+1;
	if(fclose(fp)){
		printf("can not close the file character.txt");
		exit(0);
	}
}

//构造哈夫曼树,看成有n棵树,选择权值最小的两棵树合并
void createHuffTree()
{

	int i=0,k;
	int minI,minJ;
	int f=0;
	minI=minJ=-1; //minI<minJ
	for(k=n;k<2*n-1;k++){
		//寻找ht中权值最小且无父结点的两个结点
		i=0;
		f=0;
    	while(ht[i].ch!='\0'){
    		if(ht[i].parent==-1){
	    		if(f==0){
            		minI=i;
		          	f++;
				}else if(f==1){
					if(ht[i].weight<ht[minI].weight){
						minJ=minI;
						minI=i;
					}else
			    		minJ=i;
					f++;
				}else{
			    	if(ht[i].weight<ht[minI].weight){
			    		minJ=minI;
			    		minI=i;
					}else if(ht[i].weight<ht[minJ].weight)
						minJ=i;
				}
			}
    		i++;
		}
		//合并两个结点
		ht[k].ch='#';
		ht[k].left=minI;
		ht[k].right=minJ;
		ht[k].weight=ht[minI].weight+ht[minJ].weight;
		ht[k].parent=-1;
		ht[minI].parent=ht[minJ].parent=k;
	}
}

//将一个字符串反转
void reverse(char *str)
{
	int i,j;
	char ch;
	for(i=0,j=strlen(str)-1;i<j;i++,j--){
		ch=str[i];
		str[i]=str[j];
		str[j]=ch;
	}
}

//哈夫曼编码,通过父节点从下往上找
void createHuffCode()
{
    int i,j,length;
	FILE * fp;
	for(i=0;i<n;i++){
		length=0;
		j=i;
		//给每个字符进行编码
		while(ht[j].parent!=-1){
    		if(ht[ht[j].parent].left==j){
		    	hcd[i].code[length++]=0+'0';
			}else
		    	hcd[i].code[length++]=1+'0';
			j=ht[j].parent;
		}

		hcd[i].start=hcd[i].code[length-1]-'0';
		hcd[i].code[length]='\0';
		reverse(hcd[i].code);
	}
	//把hcd字符编码写入文件document/code.txt中
	if((fp=fopen("document/code.txt","w"))==NULL){
		printf("can not open the file character.txt");
		exit(0);
	}
    for(i=0;i<n;i++){
		fputc(ht[i].ch,fp);
		fputs("    ",fp);
		fputs(hcd[i].code,fp);
		fputc('\n',fp);
	}
	if(fclose(fp)){
		printf("can not close the file character.txt");
		exit(0);
	}
}

//哈夫曼解码,每次都从根节点开始搜索
int releaseHuffCode(char *str,char* code)
{
	int root=2*n-2;
	int length=0,i=0;
	while(code[i]){
		if(code[i]=='0'+0)
			root=ht[root].left;
		else if(code[i]=='0'+1)
			root=ht[root].right;
		else
			return 0;
		if(ht[root].left==-1 && ht[root].right==-1){
	    	str[length++]=ht[root].ch;
			root=2*n-2;
		}
		i++;
	}
	str[length]='\0';
	if(root==2*n-2)
		return 1;
	return 0;
}

//用户输入编码字符
void encode()
{
	int i=0,j,f=1;
	char str[50];
	char code[500]={'\0'};
	printf("\n请输入要编码的字符串(length<50)\n");
	scanf("%s",str);
	while(str[i]){
		if((str[i]>='a'&&str[i]<='z')||(str[i]>='A'&&str[i]<='Z')){
    		for(j=0;j<n;j++)
	    		if(str[i]==ht[j].ch){
		    		strcat(code,hcd[j].code);
			    	break;
			}
	    	i++;
		}else{
			f=0;
			break;
		}
	}
	if(f)
    	puts(code);
	else
		printf("你输入的字符串错误!\n");
	printf("按任意键后重新选择!\n");
	getch();
}

//用户输入解码字串
void  decode()
{
	char str[50];
	char code[500];
	printf("\n请输入要解码的字串(用0和1表示)\n");
	scanf("%s",code);
	if(releaseHuffCode(str,code))
		puts(str);
	else
		printf("你输入的字串错误!\n");
	
	printf("按任意键后重新选择!\n");
	getch();
}

//主函数
void main()
{
	int choice=1;
    initHt();
    createHuffTree();
    createHuffCode();
    while(choice){
  	   system("cls"); 
       printf("/****************哈夫曼编码与解码*********************/\n");
	   printf(" 在document/character.txt 文件中存放着各个字母的权值\n");
	   printf(" 程序从中读出各个字母的权值构造哈夫曼树并进行编码\n");
	   printf(" 各个字符的编码存在document/code.txt文件中\n");
	   printf("/*****************************************************/\n");
	   printf("\n请输入你的选择:1 ---- 编码  2 ---- 解码  0 ---- 退出\n");
       scanf("%d",&choice);
	   switch(choice){
	   case 1: 
		   encode();
		   break;
	   case 2: 
		   decode();
		   break;
	   case 0: 
		   printf("谢谢使用!\n");
		   break;
	   default:
		   choice=1;
		   printf("你的输入错误!按任意键后重新输入!\n");
		   getch();
		   break;
	   }
   }
}

 

5
4
分享到:
评论

相关推荐

    哈夫曼编码与解码 C语言版

    绝对原创的哈夫曼编码与解码。自己输入文件名称,然后统计文件中各个字符出现的次数,计算出每个字符的哈夫曼编码和整篇文章的哈夫曼编码,然后打印出哈夫曼树。最后对整篇文章的哈夫曼编码进行解码。

    霍夫曼树实现编码解码C语言实现

    在C语言中实现霍夫曼编码和解码是一项基础且实用的技能。 首先,我们需要理解霍夫曼树的构造过程。霍夫曼树的构建基于贪心策略,通过合并频率最低的两个节点来创建新的节点,直到所有节点合并成一棵树。这个过程...

    c语言实现哈夫曼编码

    在C语言中实现哈夫曼编码涉及多个关键步骤,下面我们将详细探讨这些步骤以及如何计算平均码长。 1. **数据结构设计**:首先,我们需要定义一个数据结构来存储字符及其频率。哈夫曼树通常用二叉树表示,其中每个节点...

    哈夫曼编码译码器 C语言 数据结构课设

    这个C语言实现的哈夫曼编码译码器是学习哈夫曼编码原理和实践的一个优秀案例。 首先,我们要了解哈夫曼树的构建过程。哈夫曼树是通过将频率最低的两个节点合并,不断重复此过程,直至所有节点合并成一棵树。在这个...

    哈夫曼编码C语言程序

    在这个"哈夫曼编码C语言程序"中,开发者实现了一个C语言版本的哈夫曼编码器,能够处理输入的txt文件,并为其中的每个字符生成一个独特的二进制编码。程序的核心流程如下: 1. **字符频率统计**:首先,程序会读取`...

    哈夫曼编码与解码的程序

    在C语言中实现哈夫曼编码与解码的过程包括几个关键步骤:构造哈夫曼树、生成哈夫曼编码、编码文件和解码文件。 1. 构造哈夫曼树: - 首先,统计输入文本中每个字符出现的频率。 - 然后,创建一个最小堆(优先队列...

    哈夫曼编解码的c语言实现

    本文将详细介绍如何在C语言中实现哈夫曼编码与解码的过程。哈夫曼编码是一种广泛应用于数据压缩领域的编码方式,其核心思想是通过对不同字符采用不同长度的编码来减少整体的数据量。在哈夫曼编码中,出现频率较高的...

    哈夫曼编码解码c语言实现[定义].pdf

    在C语言中实现哈夫曼编码解码涉及到几个关键步骤: 1. **创建权值结构体**: `WeightNode` 结构体用于存储字符和对应的权值。权值通常是根据字符在文本中的频率来确定的,表示字符的重要性或出现的次数。 2. **...

    C语言哈夫曼编码与解码

    自己动手写的哈夫曼编码和解码,并带有文件操作,觉的挺好的

    用C语言实现的哈夫曼编码和解码器的源码,包括统计汉字频率、构造哈夫曼树、求解哈夫曼编码以及编码结果的写入文件等功能

    哈夫曼编码和解码器-中文汉字 1.设计目的 (1)复习并灵活掌握二叉树的各种存储结构和遍历方法, (2)了解静态链表,并掌握其构造方法。 (3)掌握哈夫曼树的构造过程和哈夫曼编码的求解方法 2.主要内容 (1)先统计某中...

    基于哈夫曼编码的文件压缩解压程序的C语言实现

    在C语言中实现基于哈夫曼编码的文件压缩解压程序,需要深入理解哈夫曼编码的基本原理以及C语言编程技巧。 首先,哈夫曼编码是根据字符出现频率进行编码的一种方法。它通过构建一棵特殊的二叉树——哈夫曼树(也称为...

    哈夫曼编码译码C语言编写[参考].pdf

    在哈夫曼编码译码C语言编写中,我们需要实现哈夫曼树的构建、哈夫曼编码的生成、哈夫曼解码的实现。下面我们将详细介绍哈夫曼编码译码的实现过程。 1. 哈夫曼树的构建 哈夫曼树是一种特殊的二叉树,它的每个节点都...

    C数据结构实现哈夫曼编码及解码

    在C环境下用数据结构数组实现哈夫曼的编码及解码,源程序 源代码 直接运行 无错误

    Huffman编码和解码的C语言实现

    编码与解码是实现数据压缩的关键技术之一。 #### Huffman编码的基本原理 Huffman编码是一种基于字符出现频率来构建编码方案的有效无损数据压缩方法。其核心思想是让出现频率较高的字符对应较短的编码,而出现频率...

    用C语言实现赫夫曼树编码

    利用c语言来实现赫夫曼树的编码,解码。适合初学者参照学习

    C语言 哈夫曼树的编码解码

    C语言 哈夫曼树的编码解码

    JPEG编解码的c语言实现

    理解并实现这个项目,你需要深入理解JPEG标准,掌握DCT计算、量化、哈夫曼编码等技术,并具备基本的C语言编程能力。此外,调试和优化代码以提高性能也是必不可少的步骤。在实际应用中,还可以考虑扩展支持其他特性,...

    哈夫曼编码解码的实现及运行截图(C语言)

    在C语言中实现哈夫曼编码和解码的过程主要包括以下几个步骤: 1. **构建哈夫曼树**: - 首先,统计输入文本中各个字符的出现频率。 - 然后,创建一个最小堆,每个元素都是一个节点,包含一个字符和其频率。 - 接...

    哈夫曼编码的 C 语言实现

    哈夫曼编码是一种无损的高效的压缩方法。对文本文件进行哈夫曼编码,使用计算信源熵打开一个文件进行概率计算,然后将输出的 submit.txt 文件用哈夫曼编码打开,之后就会对文本文件中出现的字符进行哈夫曼编码。

Global site tag (gtag.js) - Google Analytics