二叉树的存储与实现Word格式.docx

上传人:b****5 文档编号:16479555 上传时间:2022-11-24 格式:DOCX 页数:19 大小:107.65KB
下载 相关 举报
二叉树的存储与实现Word格式.docx_第1页
第1页 / 共19页
二叉树的存储与实现Word格式.docx_第2页
第2页 / 共19页
二叉树的存储与实现Word格式.docx_第3页
第3页 / 共19页
二叉树的存储与实现Word格式.docx_第4页
第4页 / 共19页
二叉树的存储与实现Word格式.docx_第5页
第5页 / 共19页
点击查看更多>>
下载资源
资源描述

二叉树的存储与实现Word格式.docx

《二叉树的存储与实现Word格式.docx》由会员分享,可在线阅读,更多相关《二叉树的存储与实现Word格式.docx(19页珍藏版)》请在冰豆网上搜索。

二叉树的存储与实现Word格式.docx

二叉树的存储与实现

实验目的及要求:

目的:

通过编程实现多项式的运算,复习数组和c语言的相关知识;

要求:

在计算机上实现整个算法。

实验硬件及软件平台:

PC机,vc++6.0,。

实验(或算法)原理:

在计算机科学中,树是一种重要的非线性数据结构,直观地看,它是数据元素(在树中称为结点)按分支关系组织起来的结构。

二叉树是每个节点最多有两个子树的有序树。

通常子树被称作“左子树”(leftsubtree)和“右子树”(rightsubtree)。

二叉树常被用于实现二叉查找树和二叉堆。

值得注意的是,二叉树不是树的特殊情形。

在图论中,二叉树是一个连通的无环图,并且每一个顶点的度不大于3。

有根二叉树还要满足根结点的度不大于2。

有了根结点后,每个顶点定义了唯一的根结点,和最多2个子结点。

然而,没有足够的信息来区分左结点和右结点。

以哈夫曼树─即最优二叉树,带权路径长度最小的二叉树,经常应用于数据压缩。

在计算机信息处理中,“哈夫曼编码”是一种一致性编码法(又称“熵编码法”),用于数据的无损耗压缩。

这一术语是指使用一张特殊的编码表将源字符(例如某文件中的一个符号)进行编码。

这张编码表的特殊之处在于,它是根据每一个源字符出现的估算概率而建立起来的(出现概率高的字符使用较短的编码,反之出现概率低的则使用较长的编码,这便使编码之后的字符串的平均期望长度降低,从而达到无损压缩数据的目的)。

这种方法是由David.A.Huffman发展起来的。

例如,在英文中,e的出现概率很高,而z的出现概率则最低。

当利用哈夫曼编码对一篇英文进行压缩时,e极有可能用一个位(bit)来表示,而z则可能花去25个位(不是26)。

用普通的表示方法时,每个英文字母均占用一个字节(byte),即8个位。

二者相比,e使用了一般编码的1/8的长度,z则使用了3倍多。

倘若我们能实现对于英文中各个字母出现概率的较准确的估算,就可以大幅度提高无损压缩的比例。

实验步骤:

1.根据算法事先写出相应程序。

2.启动PC机,进入vc集成环境,输入代码。

3.编译调试。

4.调试通过,计算出正确结果。

实验内容(包括实验具体内容、算法分析、源代码等等):

#include<

iostream.h>

iomanip.h>

string.h>

malloc.h>

stdio.h>

//typedefintTElemType;

constintUINT_MAX=1000;

charstr[50];

typedefstruct

{

intweight,K;

intparent,lchild,rchild;

}HTNode,*HuffmanTree;

typedefchar**HuffmanCode;

//-----------全局变量-----------------------

HuffmanTreeHT;

HuffmanCodeHC;

intw[50],i,j,n;

charz[50];

intflag=0;

intnumb=0;

//-----------------求赫夫曼编码-----------------------

structcou{

chardata;

intcount;

}cou[50];

intmin(HuffmanTreet,inti)

{//函数voidselect()调用

intj,flag;

intk=UINT_MAX;

//取k为不小于可能的值,即k为最大的权值1000

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;

returnflag;

}

//--------------------slect函数----------------------

voidselect(HuffmanTreet,inti,int&

s1,int&

s2)

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

intj;

s1=min(t,i);

s2=min(t,i);

if(s1>

j=s1;

s1=s2;

s2=j;

//--------------算法6.12--------------------------

voidHuffmanCoding(HuffmanTree&

HT,HuffmanCode&

HC,int*w,intn)

{//w存放n个字符的权值(均>

0),构造赫夫曼树HT,并求出n个字符的赫夫曼编码HC

intm,i,s1,s2,start;

//unsignedc,f;

intc,f;

HuffmanTreep;

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;

parent=0;

lchild=0;

rchild=0;

}

for(;

=m;

++i,++p)

for(i=n+1;

++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].lchild=s1;

HT[i].rchild=s2;

HT[i].weight=HT[s1].weight+HT[s2].weight;

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

HC=(HuffmanCode)malloc((n+1)*sizeof(char*));

//分配n个字符编码的头指针向量([0]不用)

cd=(char*)malloc(n*sizeof(char));

//分配求编码的工作空间

cd[n-1]='

\0'

;

//编码结束符

for(i=1;

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]='

0'

else

1'

HC[i]=(char*)malloc((n-start)*sizeof(char));

//为第i个字符编码分配空间

strcpy(HC[i],&

cd[start]);

//从cd复制编码(串)到HC

free(cd);

//释放工作空间

//---------------------获取报文并写入文件---------------------------------

intInputCode()

//cout<

<

"

请输入你想要编码的字符"

endl;

FILE*tobetran;

if((tobetran=fopen("

tobetran.txt"

"

w"

))==NULL)

cout<

不能打开文件"

return0;

gets(str);

fputs(str,tobetran);

获取报文成功"

fclose(tobetran);

returnstrlen(str);

//--------------初始化赫夫曼链表---------------------------------

voidInitialization()

{inta,k,flag,len;

a=0;

len=InputCode();

for(i=0;

len;

{k=0;

flag=1;

cou[i-a].data=str[i];

cou[i-a].count=1;

while(i>

k)

if(str[i]==str[k])

a++;

flag=0;

k++;

if(flag==0)

break;

if(flag)

for(j=i+1;

j++)

{if(str[i]==str[j])

++cou[i-a].count;

n=len-a;

n;

{cout<

cou[i].data<

"

cou[i].count<

{*(z+i)=cou[i].data;

*(w+i)=cou[i].count;

HuffmanCoding(HT,HC,w,n);

//------------------------打印编码-------------------------------------------

字符对应的编码为:

puts(HC[i]);

//--------------------------将赫夫曼编码写入文件------------------------

下面将赫夫曼编码写入文件"

endl<

...................."

FILE*htmTree;

charr[]={'

'

'

};

if((htmTree=fopen("

htmTree.txt"

))==NULL)

cannotopenfile"

fputs(z,htmTree);

n+1;

fprintf(htmTree,"

%6d"

*(w+i));

fputs(r,htmTree);

fputs(HC[i],htmTree);

fclose(htmTree);

已将字符与对应编码写入根目录下文件htmTree.txt中"

//---------------------编码函数---------------------------------

voidEncoding()

下面对目录下文件tobetran.txt中的字符进行编码"

FILE*tobetran,*codefile;

rb"

if((codefile=fopen("

codefile.txt"

wb"

char*tran;

i=99;

tran=(char*)malloc(100*sizeof(char));

while(i==99)

if(fgets(tran,100,tobetran)==NULL)

*(tran+i)!

='

for(j=0;

if(*(z+j-1)==*(tran+i))

fputs(HC[j],codefile);

if(j>

n)

字符错误,无法编码!

编码工作完成"

编码写入目录下的codefile.txt中"

fclose(codefile);

free(tran);

//-----------------译码函数---------------------------------

voidDecoding()

下面对根目录下文件codefile.txt中的字符进行译码"

FILE*codef,*txtfile;

if((txtfile=fopen("

txtfile.txt"

if((codef=fopen("

r"

char*work,*work2,i2;

inti4=0,i,i3;

unsignedlonglength=10000;

work=(char*)malloc(length*sizeof(char));

fgets(work,length,codef);

work2=(char*)malloc(length*sizeof(char));

i3=2*n-1;

*(work+i-1)!

i2=*(work+i);

if(HT[i3].lchild==0)

*(work2+i4)=*(z+i3-1);

i4++;

i--;

elseif(i2=='

)i3=HT[i3].lchild;

)i3=HT[i3].rchild;

*(work2+i4)='

fputs(work2,txtfile);

译码完成"

内容写入根目录下的文件txtfile.txt中"

free(work);

free(work2);

fclose(txtfile);

fclose(codef);

//-----------------------打印编码的函数----------------------

voidCode_printing()

下面打印根目录下文件CodePrin.txt中编码字符"

FILE*CodePrin,*codefile;

if((CodePrin=fopen("

CodePrin.txt"

char*work3;

work3=(char*)malloc(51*sizeof(char));

do

if(fgets(work3,51,codefile)==NULL)

不能读取文件"

fputs(work3,CodePrin);

puts(work3);

}while(strlen(work3)==50);

free(work3);

打印工作结束"

fclose(CodePrin);

//-------------------------------打印译码函数---------------------------------------------

voidCode_printing1()

下面打印根目录下文件txtfile.txt中译码字符"

FILE*CodePrin1,*txtfile;

if((CodePrin1=fopen("

CodePrin1.txt"

char*work5;

work5=(char*)malloc(51*sizeof(char));

if(fgets(work5,51,txtfile)==NULL)

fputs(work5,CodePrin1);

puts(work5);

}while(strlen(work5)==50);

free(work5);

fclose(CodePrin1);

//------------------------打印赫夫曼树的函数-----------------------

voidcoprint(HuffmanTreestart,HuffmanTreeHT)

if(start!

=HT)

{FILE*TreePrint;

if((TreePrint=fopen("

TreePrint.txt"

a"

{cout<

创建文件失败"

numb++;

//该变量为已被声明为全局变量

coprint(HT+start->

rchild,HT);

setw(5*numb)<

start->

weight<

fprintf(TreePrint,"

%d\n"

start->

weight);

lchild,HT);

numb--;

fclose(TreePrint);

voidTree_printing(HuffmanTreeHT,intw)

p=HT+w;

下面打印赫夫曼树"

coprint(p,HT);

//------------------------主函数------------------------------------

voidmain()

charchoice;

while(choice!

q'

\n******************************"

欢迎使用赫夫曼编码解码系统"

******************************"

(1)要初始化赫夫曼链表请输入'

i'

(2)要编码请输入'

e'

(3)要译码请输入'

d'

(4)要打印编码请输入'

p'

(5)要打印赫夫曼树请输入'

t'

(6)要打印译码请输入'

y'

if(flag==0)cout<

\n请先初始化赫夫曼链表,输入'

cin>

>

choice;

switch(choice)

case'

:

Initialization();

Encoding();

Decoding();

Code_printing();

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

当前位置:首页 > 法律文书 > 辩护词

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

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