信息理论与编码实验指导书.docx

上传人:b****5 文档编号:7279321 上传时间:2023-01-22 格式:DOCX 页数:45 大小:99.15KB
下载 相关 举报
信息理论与编码实验指导书.docx_第1页
第1页 / 共45页
信息理论与编码实验指导书.docx_第2页
第2页 / 共45页
信息理论与编码实验指导书.docx_第3页
第3页 / 共45页
信息理论与编码实验指导书.docx_第4页
第4页 / 共45页
信息理论与编码实验指导书.docx_第5页
第5页 / 共45页
点击查看更多>>
下载资源
资源描述

信息理论与编码实验指导书.docx

《信息理论与编码实验指导书.docx》由会员分享,可在线阅读,更多相关《信息理论与编码实验指导书.docx(45页珍藏版)》请在冰豆网上搜索。

信息理论与编码实验指导书.docx

信息理论与编码实验指导书

 

信息理论与编码实验指导书

 

解振东编写

 

 

信息科学与技术学院

实验一:

香农(Shannon)编码

一、实验目的

掌握通过计算机实现香农编码的方法。

二、实验要求

对于给定的信源的概率分布,按照香农编码的方法进行计算机实现。

三、实验基本原理

给定某个信源符号的概率分布,通过以下的步骤进行香农编码

1.将信源消息符号按其出现的概率大小排列

2.确定满足下列不等式的整数码长Ki;

3.为了编成唯一可译码,计算第i个消息的累加概率

4.将累加概率Pi变换成二进制数。

5.取Pi二进制数的小数点后Ki位即为该消息符号的二进制码。

四实验内容

1.对给定信源

进行二进制香农编码。

2.对给定信源

进行二进制香农编码。

3.自已选择一个例子进行香农编码。

五、实验设备

PC计算机,C++

六、实验报告要求

1、画出程序设计的流程图,

2、写出程序代码,

3、写出在调试过程中出现的问题,

4、对实验的结果进行分析。

七、参考程序(仅供参考)

//香农(Shannon)编码参考程序

intmain()

{

intN;

cout<<”请输入信源符号个数:

”;cin>>N;

cout<<”请输入各符号的概率:

”<

double*X=newdouble[N];//离散无记忆信源

inti,j;

for(i=0;i

{

cout<<”X[”<>X[i];

}

//由小到大排序

for(i=0;i

for(j=i+1;j

if(X[i]

{doubletemp=X[i];X[i]=X[j];X[j]=temp;}

int*K=newint[N];//确定码长

for(i=0;i

{

K[i]=int(-(log(X[i])/log

(2)))+1;//确认码长为1-log2(p(xi))

if(K[i]==(-(log(X[i])/log

(2)))+1)//当K[i]=-log2(p(xi))时,K[i]--

K[i]--;

}

//累加概率

double*Pa=newdouble[N];pa[0]=0.0;

for(i=1;i

pa[i]=pa[i-1]+X[i-1];

//将累加概率转换为二进制

string*code=newstring[N];

for(i=0;i

for(j=0;j

{

doubletemp=Pa[i]*2;

if(temp>=1)//累加概率乘2大于1,对应码字加1,累加概率自身取余

{

code[i]+=”1”;

Pa[i]=Pa[i]*2-1;

}

else//累加概率乘2小于1时,对应码字加0,累加概率自身取余

{

code[i]+=”0”;

Pa[i]*=2;

}

}

for(i=0;i

code[i]=code[i].substr(0,K[i]);//求码字

//输出码字

cout<

for(i=0;i

cout<

delete[]X;

delete[]Pa;

delete[]K;

delete[]code;

getch();

retuen0;

}

 

实验二费诺编码

一、实验目的

掌握通过计算机实现费诺编码。

二、实验要求

对于给定的信源的概率分布,按照费诺编码的方法进行计算机实现。

三、实验基本原理

费诺编码的步骤:

1.将概率按从大到小的顺序排列;

2.按编码进制数将概率分组,使每组概率和尽可能接近或相等;

3.给每组分配一位码元;

4.将每一分组再按同样原则划分,重复2和3,直到概率不再可分为止。

四实验内容

1.对给定信源

进行二进制费诺编码。

2.对给定信源

进行二进制费诺编码。

3.自已选择一个例子进行费诺编码。

五、实验设备

PC计算机,C++

六、实验报告要求

1、画出程序设计的流程图,

2、写出程序代码,

3、写出在调试过程中出现的问题,

4、对实验的结果进行分析。

七、参考程序(仅供参考)

//********费诺编码参考程序1****

//全局变量定义

intn;

string*sign;

double*p;

string*code;

voidfano(inta,intb)//费诺编码函数

{

if((b-a)>=1)//判断该组中符号个数是否大于2

{

doublesum=0;

for(inti=a;i<=b;i++)

sum+=p[i];//计算该组概率累加和

doubles1=0,*s=newdouble[10];

for(inti=a;i<=b;i++)

{

s1+=p[i];s[i]=fabs(2*s1-sum)/sum;

}

doublemin=s[a];intc;

for(inti=a;i<=b;i++)

if(s[i]<=min)

{

min=s[i];c=i;//定位使两组概率和尽可能相近或相等的位置c

}

for(inti=a;i<=b;i++)

{

if(i<=c)code[i]+=”0”;//码字加“0”

elsecode[i]+=”1”;//码字加“1”

}

//判断分组点位置,进而分情况自身调用

if(c==a)

fano(c+1,b);

elseif(c==b-1)

fano(a,c);

else

{fano(a,c);fano(c+1,b);}

}

}

voidmain()

{

cout<<””请输入信源符号个数n:

”;

cin>>n;

p=newdouble[n];

sign=newstring[n];

code=newstring[n];

cout<<”请输入信源符号:

”;

for(inti=0;i>sign[i];

cout<<”请输入信源符号的概率:

”;

for(inti=0;i>p[i];

for(inti=0;i

for(intj=i+1;j

if(p[i]

{

doubletemp=p[i];p[i]=p[j];p[j]=temp;

stringm=sign[i];sign[i]=sign[j];sign[j]=m;

}

fano(0,n-1);//费诺编码

cout<

for(inti=0;i

cout<

delete[]p;delete[]sign;delete[]code;

}

//***********费诺编码参考程序2*************

#include

#include

usingnamespacestd;

classDATA//数据类,采用双向表

{

public:

//初始化PXi=1是为了在排序迭代时方便

DATA(){next=NULL;pre=NULL;r=NULL;PXi=1;key[0]='\0';key[1]='\0';key[2]='\0';key[3]='\0';key[4]='\0';key[5]='\0';

key[6]='\0';key[7]='\0';key[8]='\0';key[9]='\0';key[10]='\0';}

charXi;//信源符号

doublePXi;//信源概率

charkey[11];//码字

DATA*next,*pre,*r;//地址

};

DATA*head=newDATA,*p=head;

intk=(-1);//编码函数用

voidencoding(DATA*pp);//编码函数声明

DATA*sort(DATA*pp);//排序函数声明

DATA*HEAD=newDATA,*tt=HEAD,*T;//排序函数用

voidinput()//输入数据

{

doublel,sum=0;

intn,i;

charL;

cout<<"请输入信源个数:

";

cin>>n;

for(i=0;i

{

cout<<"请输入一个字符的信源符号:

"<>L;

cout<<"请输入概率:

"<>l;

p->Xi=L;

p->PXi=l;

sum=sum+p->PXi;

p->next=newDATA;

p->next->pre=p;//对新创建结点赋值

p->r=p->next;

p=p->next;

}

if(sum!

=1)

{

cout<<"所输入的概率之和是"<

input();

}

T=sort(head);//因为sort要改变tt,故需要一个中间变量

tt->next=T;//由于迭代产生的链表格式不规范,以下句用来整理sort函数的返回结果

tt->next->pre=tt;

tt=tt->next;

tt->next=newDATA;

tt->next->pre=tt;//对新创建结点赋值

tt=tt->next;

HEAD->next->next->pre=NULL;

HEAD=HEAD->next->next;

cout<<"对输入信源排序结果如下:

"<

for(p=HEAD;p->next!

=NULL;p=p->next)//排序输出

cout<Xi<<":

"<PXi<

cout<<"对输入信源编码结果如下:

"<

encoding(HEAD);

}

/***********************编码************************/

voidencoding(DATA*pp)//定义递归函数

{

doubley=1;//y定义为1是因为概率最多为1

k++;//递归自增值,用于字符数组定位

DATA*head1=pp,*head2;

into=1;

while

(1)//分01组

{

doublel=0,z=0;

for(inti=1;i<=o;i++)

{

if(pp->next==NULL)break;

l=l+pp->PXi;

pp=pp->next;

}

head2=pp->pre;//从这里分01段

for(;pp->next!

=NULL;pp=pp->next)

z=z+pp->PXi;

if(y>fabs(l-z))//判断两组值之差是否最小

{

y=fabs(l-z);

pp=head1;

o++;

continue;

}

elseif(z==0&&i<=2)//z=0,i<1表示只有一个概率了

{

cout<Xi<<":

"<key<

break;

}

for(DATA*u=head1;u->next!

=head2->next;u=u->next)

u->key[k]='0';//为字符串赋值

for(DATA*h=head2;h->next!

=NULL;h=h->next)

h->key[k]='1';

head2->pre->next=newDATA;//分段:

标记head2为上一段结束位置

head2->pre->next->pre=head2->pre;

encoding(head1);//递归

encoding(head2);

break;

}

k--;//迭代还原到上一个数组位置

}

DATA*sort(DATA*pp)

{//函数递归后头变到HEAD->next->next.返回值得到最后个head2没有与tt相连,需另设.得不到结尾为空的(next=MULL)地址

DATA*head1=pp,*head2=pp;

if(pp->next==NULL)returnpp;//当pp是最后一个值时

for(;pp->next!

=NULL;pp=pp->next)

{

if(1-pp->PXi>=1-head2->PXi)//两个以上的值时,由于最后一个pxi为1,所以每次都会有个最小值

head2=pp;

}

if(head2->pre==NULL)//当pp是第一个值时

{

head2->next->pre=NULL;

head1=head1->next;

}

else//当pp是最后一个值及中间的值时

{

head2->pre->next=head2->next;

head2->next->pre=head2->pre;

}

tt->next=sort(head1);//递归,先得第一个,再得下一个

tt->next->pre=tt;

tt=tt->next;

returnhead2;

}

voidmain()

{

cout<<"************费诺编码************"<

input();

cout<

}

 

实验三霍夫曼编码

一、实验目的

掌握通过计算机实现霍夫曼编码

二、实验要求

对于给定的信源的概率分布,按照霍夫曼编码的方法进行计算机实现。

三、实验基本原理

霍夫曼编码的步骤:

(1).把信源符号按概率大小顺序排列,并设法按逆次序分配码字的长度。

(2).在分配码字长度时,首先将出现概率最小的两个符号的概率相加合成一个概率

(3).把这个合成概率看成是一个新组合符号地概率,重复上述做法直到最后只剩下两个符号概率为止。

(4).完成以上概率顺序排列后,再反过来逐步向前进行编码,每一次有二个分支各赋予一个二进制码,可以对概率大的赋为0,概率小的赋为1。

四实验内容

1.对给定信源

进行二进制霍夫曼编码。

2.对给定信源

进行二进制霍夫曼编码。

3.自已选择一个例子进行霍夫曼编码。

五、实验设备

PC计算机,C++

六、实验报告要求

1、画出程序设计的流程图,

2、写出程序代码,

3、写出在调试过程中出现的问题,

4、对实验的结果进行分析。

七、参考程序(仅供参考)

//第一段参考代码

#include

#include

#include//forsetw

usingnamespacestd;

//====================

typedefstruct

{

intweight;

intparent;

intlchild;

intrchild;

}hnodetype;//霍夫曼树节点

typedefstruct

{

intbit[10];

intposition;

charsign;

}hcodetype;//霍夫曼编码表

//=======================

voidHuffman(intm[],intn);//函数声明

intmain()

{

inti=0,n=8;

intm[10]={40,18,10,10,7,6,5,4};

charsign[10]="hufmcode";

cout<

";

for(i=0;i

cout<

cout<

";

for(i=0;i

{

floatf=(float)m[i]/100;

cout<

}

cout<

"<

Huffman(m,n);

getch();

return0;

}

//====================================

voidHuffman(intm[],intn)

{

inti,j,m1,m2,x1,x2,c,p;

hnodetype*huffnode=newhnodetype[2*n-1];//一共2n-1个节点

hcodetype*huffcode=newhcodetype[n],temp;

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

{//初始化霍夫曼树

huffnode[i].weight=0;

huffnode[i].parent=0;

huffnode[i].lchild=1;

huffnode[i].rchild=1;

}

for(i=0;i

{//节点赋初值

huffnode[i].weight=m[i];

huffcode[i].sign=sign[i];

}

//对n到2n-1节点编码

for(i=0;i

{

m1=m2=100;

x1=x2=0;

for(j=0;j

{

if(huffnode[j].weight<=m1&&huffnode[j].parent==0)

{

m2=m1;x2=x1;

m1=huffnode[j].weight;

x1=j;

}

elseif(huffnode[j].weight<=m2&&huffnode[j].parent==0)

{

m2=huffnode[j].weight;

x2=j;

}

}

huffnode[x1].parent=n+i;//定义x1和x2的父节点为n+i

huffnode[x2].parent=n+i;

huffnode[n+i].weight=huffnode[x1].weight+huffnode[x2].weight;

huffnode[n+i].lchild=x1;//新节点的左、右孩子分别为x1、x2

huffnode[n+i].rchild=x2;

}

//从叶子到根逆向求每个字符的霍夫曼编码

for(i=0;i

{

temp.position=n-1;

c=i;

p=huffnode[c].parent;

while(p!

=0)//如果p节点不是根节点则一直向上编码

{

if(huffnode[p].lchild==c)//如果p节点的左孩子是c,则码字加1

temp.bit[temp.position]=1;

else//否则则码字加0

temp.bit[temp.position]=0;

temp.position--;//记录当前码字存储位置

c=p;p=huffnode[c].parent;//从新定义c和p的指向

}

cout<

";

for(j=temp.position+1;j

{//输出码字

huffcode[i].bit[j]=temp.bit[j];

cout<

}

cout<

}

delete[]huffcode;

delete[]huffnode;

}

//第二段参考代码

#include

#include

#include

#include

#include

//------

typedefstruct{

unsignedintweight;

unsignedintparent,lchild,rchild;

}HTNode,*HuffmanTree;

typedefchar**HuffmanCode;

typedefstruct{

unsignedints1;

unsignedints2;

}MinCode;

voidError(char*message);

HuffmanCodeHuffmanCoding(HuffmanTreeHT,HuffmanCodeHC,unsignedint*w,unsignedintn);

MinCodeSelect(HuffmanTreeHT,unsignedintn);

voidError(char*message)

{

clrscr();

fprintf(stderr,"Error:

%s",message);

exit

(1);

}

HuffmanCodeHuffmanCoding(HuffmanTreeHT,HuffmanCodeHC,unsignedint*w,unsignedintn)

{

unsignedinti,s1=0,s2=0;

HuffmanTreep;

char*cd;

unsignedintf,c,start,m;

MinCodemin;

if(n<=1)Error("Codetoosmall!

");

m=2*n-1;

HT=(HuffmanTree)malloc((m+1)*sizeof(HTNode));

for(p=HT,i=0;i<=n;i++,p++,w++)

{

p->weight=*w;

p->parent=0;

p->lchild=0;

p->r

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 农林牧渔 > 林学

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1