怎么样用c语言程序编码哈夫曼树?

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了怎么样用c语言程序编码哈夫曼树?相关的知识,希望对你有一定的参考价值。

用程序代码写出并加有注释

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include <ctype.h>
#include<limits.h>
int function1(char ch,char *s)

int i;
for(i=0; s[i]!='\0'; i++)

if(ch==s[i])return 0;

return 1;

typedef struct

unsigned int weight;
unsigned int parent,lchild,rchild;
HTNode,*HuffmanTree; // 动态分配数组存储赫夫曼树
typedef char **HuffmanCode; // 动态分配数组存储赫夫曼编码表
// algo6-1.cpp 求赫夫曼编码。实现算法6.12的程序

int min(HuffmanTree t,int i)

// 函数void select()调用
int j,flag;
unsigned int k=UINT_MAX; // 取k为不小于可能的值
for(j=1; j<=i; j++)
if(t[j].weight<k&&t[j].parent==0)
k=t[j].weight,flag=j;
t[flag].parent=1;
return flag;


void select(HuffmanTree t,int i,int &s1,int &s2)

// s1为最小的两个值中序号小的那个

s1=min(t,i);
s2=min(t,i);
/* if(s1>s2)

j=s1;
s1=s2;
s2=j;
*/


void HuffmanCoding(HuffmanTree &HT,HuffmanCode &HC,int *w,int n) // 算法6.12

// w存放n个字符的权值(均>0),构造赫夫曼树HT,并求出n个字符的赫夫曼编码HC
int m,i,s1,s2,start;
unsigned c,f;
HuffmanTree p;
char *cd;
if(n<=1)
return;
m=2*n-1;
HT=(HuffmanTree)malloc((m+1)*sizeof(HTNode)); // 0号单元未用
for(p=HT+1,i=1; i<=n; ++i,++p,++w)

(*p).weight=*w;
(*p).parent=0;
(*p).lchild=0;
(*p).rchild=0;

for(; i<=m; ++i,++p)
(*p).parent=0;
for(i=n+1; i<=m; ++i) // 建赫夫曼树

// 在HT[1~i-1]中选择parent为0且weight最小的两个结点,其序号分别为s1和s2
select(HT,i-1,s1,s2);
HT[s1].parent=HT[s2].parent=i;
HT[i].rchild=s1;
HT[i].lchild=s2;
HT[i].weight=HT[s1].weight+HT[s2].weight;
// printf("HT[%d].lchild:%d HT[%d].rchild:%d\n",i,s2,i,s1);

// 从叶子到根逆向求每个字符的赫夫曼编码
HC=(HuffmanCode)malloc((n+1)*sizeof(char*));
// 分配n个字符编码的头指针向量([0]不用)
cd=(char*)malloc(n*sizeof(char)); // 分配求编码的工作空间
cd[n-1]='\0'; // 编码结束符
for(i=1; i<=n; i++)

// 逐个字符求赫夫曼编码
start=n-1; // 编码结束符位置
for(c=i,f=HT[i].parent; f!=0; c=f,f=HT[f].parent)
// 从叶子到根逆向求编码
if(HT[f].lchild==c)
cd[--start]='1';
else
cd[--start]='0';
HC[i]=(char*)malloc((n-start)*sizeof(char));
// 为第i个字符编码分配空间
strcpy(HC[i],&cd[start]); // 从cd复制编码(串)到HC

free(cd); // 释放工作空间

void swap1(int *a ,int *b)

int t;
t=*a;
*a=*b;
*b=t;

void swap2(char *a,char *b)

char ch;
ch=*a;
*a=*b;
*b=ch;

int main(void)

HuffmanTree HT;
HuffmanCode HC;
char *s1,*s2;
int i,j=0,n,count,*m,t,flag=1;
scanf("%d",&n);
getchar();
s1=(char*)malloc((n+n)*sizeof(char));
s2=(char*)malloc(n*sizeof(char));
memset(s2,'\0',n*sizeof(char));
gets(s1);
count=strlen(s1);
for(i=0; i<count; i++)

if(!isspace(*(s1+i)))

if(function1(*(s1+i),s2))

*(s2+j)=*(s1+i);
j++;


else;

m=(int*)malloc(j*sizeof(int));
for(i=0; i<j; i++)
*(m+i)=0;
for(t=0; t<j; t++)

for(i=0; i<count; i++)

if(*(s2+t)==*(s1+i))
*(m+t)+=1;


for(i=0;i<j;i++)
while(flag)

flag = 0;
for (t=0; t<j-1; t++)

if(*(m+t)<*(m+t+1))

swap1(m+t,m+t+1);
swap2(s2+t,s2+t+1);
flag=1;



HuffmanCoding(HT,HC,m,j);
for(i=1,t=0; i<=j; i++,t++)

printf("%c %d %s\n",*(s2+t),*(m+t),HC[i]);


return 0;
参考技术A #include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include
<ctype.h>
#include<limits.h>
int
function1(char
ch,char
*s)

int
i;
for(i=0;
s[i]!='\0';
i++)

if(ch==s[i])return
0;

return
1;

typedef
struct

unsigned
int
weight;
unsigned
int
parent,lchild,rchild;

HTNode,*HuffmanTree;
//
动态分配数组存储赫夫曼树
typedef
char
**HuffmanCode;
//
动态分配数组存储赫夫曼编码表
//
algo6-1.cpp
求赫夫曼编码。实现算法6.12的程序
int
min(HuffmanTree
t,int
i)

//
函数void
select()调用
int
j,flag;
unsigned
int
k=UINT_MAX;
//
取k为不小于可能的值
for(j=1;
j<=i;
j++)
if(t[j].weight<k&&t[j].parent==0)
k=t[j].weight,flag=j;
t[flag].parent=1;
return
flag;

void
select(HuffmanTree
t,int
i,int
&s1,int
&s2)

//
s1为最小的两个值中序号小的那个
s1=min(t,i);
s2=min(t,i);
/*
if(s1>s2)

j=s1;
s1=s2;
s2=j;
*/

void
HuffmanCoding(HuffmanTree
&HT,HuffmanCode
&HC,int
*w,int
n)
//
算法6.12

//
w存放n个字符的权值(均>0),构造赫夫曼树HT,并求出n个字符的赫夫曼编码HC
int
m,i,s1,s2,start;
unsigned
c,f;
HuffmanTree
p;
char
*cd;
if(n<=1)
return;
m=2*n-1;
HT=(HuffmanTree)malloc((m+1)*sizeof(HTNode));
//
0号单元未用
for(p=HT+1,i=1;
i<=n;
++i,++p,++w)

(*p).weight=*w;
(*p).parent=0;
(*p).lchild=0;
(*p).rchild=0;

for(;
i<=m;
++i,++p)
(*p).parent=0;
for(i=n+1;
i<=m;
++i)
//
建赫夫曼树

//
在HT[1~i-1]中选择parent为0且weight最小的两个结点,其序号分别为s1和s2
select(HT,i-1,s1,s2);
HT[s1].parent=HT[s2].parent=i;
HT[i].rchild=s1;
HT[i].lchild=s2;
HT[i].weight=HT[s1].weight+HT[s2].weight;
//
printf("HT[%d].lchild:%d
HT[%d].rchild:%d\n",i,s2,i,s1);

//
从叶子到根逆向求每个字符的赫夫曼编码
HC=(HuffmanCode)malloc((n+1)*sizeof(char*));
//
分配n个字符编码的头指针向量([0]不用)
cd=(char*)malloc(n*sizeof(char));
//
分配求编码的工作空间
cd[n-1]='\0';
//
编码结束符
for(i=1;
i<=n;
i++)

//
逐个字符求赫夫曼编码
start=n-1;
//
编码结束符位置
for(c=i,f=HT[i].parent;
f!=0;
c=f,f=HT[f].parent)
//
从叶子到根逆向求编码
if(HT[f].lchild==c)
cd[--start]='1';
else
cd[--start]='0';
HC[i]=(char*)malloc((n-start)*sizeof(char));
//
为第i个字符编码分配空间
strcpy(HC[i],&cd[start]);
//
从cd复制编码(串)到HC

free(cd);
//
释放工作空间

void
swap1(int
*a
,int
*b)

int
t;
t=*a;
*a=*b;
*b=t;

void
swap2(char
*a,char
*b)

char
ch;
ch=*a;
*a=*b;
*b=ch;

int
main(void)

HuffmanTree
HT;
HuffmanCode
HC;
char
*s1,*s2;
int
i,j=0,n,count,*m,t,flag=1;
scanf("%d",&n);
getchar();
s1=(char*)malloc((n+n)*sizeof(char));
s2=(char*)malloc(n*sizeof(char));
memset(s2,'\0',n*sizeof(char));
gets(s1);
count=strlen(s1);
for(i=0;
i<count;
i++)

if(!isspace(*(s1+i)))

if(function1(*(s1+i),s2))

*(s2+j)=*(s1+i);
j++;


else;

m=(int*)malloc(j*sizeof(int));
for(i=0;
i<j;
i++)
*(m+i)=0;
for(t=0;
t<j;
t++)

for(i=0;
i<count;
i++)

if(*(s2+t)==*(s1+i))
*(m+t)+=1;


for(i=0;i<j;i++)
while(flag)

flag
=
0;
for
(t=0;
t<j-1;
t++)

if(*(m+t)<*(m+t+1))

swap1(m+t,m+t+1);
swap2(s2+t,s2+t+1);
flag=1;



HuffmanCoding(HT,HC,m,j);
for(i=1,t=0;
i<=j;
i++,t++)

printf("%c
%d
%s\n",*(s2+t),*(m+t),HC[i]);

return
0;

霍夫曼编码的编码效率怎么求?

主要是为了比较霍夫曼编码与费诺编码孰优孰劣

求效率首先要求得信号的熵,也就是最小的编码长度,比如是2.3,然后再求霍夫曼码的平均编码长度(各个概率和码位相乘再求和)比如是2.7,那么效率就是0.85。

霍夫曼编码的编码效率,我想可以用压缩率来表示吧。随机选取一段字符,计算其编码长度为 n。再对其用霍夫曼编码,得到长度为 m。于是 m/n 就是压缩率。

霍夫曼编码是变长编码,思路:对概率大的编的码字短,概率小的编的码字长,这样一来所编的总码长就小,这样编码效率就高。

扩展资料:

在计算机数据处理中,霍夫曼编码使用变长编码表对源符号(如文件中的一个字母)进行编码,其中变长编码表是通过一种评估来源符号出现机率的方法得到的,出现机率高的字母使用较短的编码,反之出现机率低的则使用较长的编码,这便使编码之后的字符串的平均长度、期望值降低,从而达到无损压缩数据的目的。

参考资料来源:百度百科-霍夫曼编码

参考技术A 求效率首先要求得信号的熵,也就是最小的编码长度,比如是2.3,然后再求霍夫曼码的平均编码长度(各个概率和码位相乘再求和)比如是2.7,那么效率就是0.85 参考技术B 霍夫曼编码是变长编码,思路:对概率大的编的码字短,概率小的编的码字长,这样一来所编的总码长就小,这样编码效率就高。你上面那样求是不对的,除非你 参考技术C 霍夫曼编码的编码效率,我想可以用压缩率来表示吧。随机选取一段字符,计算其编码长度为 n。再对其用霍夫曼编码,得到长度为 m。于是 m/n 就是压缩率。

以上是关于怎么样用c语言程序编码哈夫曼树?的主要内容,如果未能解决你的问题,请参考以下文章

哈夫曼编码C语言实现

哈夫曼树定义及其构造和编码(C语言)

哈夫曼树(C语言实现)

h5房卡源码C语言实现哈夫曼树编码解码及问题总结

C++程序编写压缩器/解压器(长度-游程编码的压缩/解压+霍夫曼编码压缩/解压 (霍夫曼树))

求哈夫曼解码C语言程序 请各位大侠在我原有的程序上加上哈夫曼解码的程序,不胜感激!