当前位置:首页 » 操作系统 » 算法WPL

算法WPL

发布时间: 2022-10-21 23:53:26

❶ 哈夫曼树算法

题目的阐述:以N进制编码方式对一个英文字串中的字符进行编码,每个不同的字符其编码不同.使得由新的编码替代原串后总码长最小,且输入0,1,2,...,N-1构成的数字串后,依照该编码方式可以正确的对译出唯一的英文原串.如:N=3英文原串为ABBCBADDACE其对应的一种编码方式为A:00B:01C:020D:021E:022原串对译后的编码为000101020010002102100020022其码长为27若输入编码串0102002200则对应的英文原串为BCEA 分析: 假设英文原串中的字符存放于字符集S中,‖S‖=X,每个字符在字串中出现的概率为W[i],L[i]为字符i的编码长.依题意得,对S集合中的不同字符进行N进制编码后要求1)新字串的码长最短WPL=∑W[i]*L[i]
(i∈1..X)使得在WPL是所有编码方式中的最小值2)编码无二义性任意一字符编码都不为其它字符编码的前缀 此题以哈夫曼树来解答是非常适宜的.N为此哈夫曼树的分叉数,S字符集里的元素即为此N叉哈夫曼树的叶子,概率W[i]即为叶子结点的权重,从根结点到各叶子结点的路径长即为该叶子结点的编码长L[i].由哈夫曼树的思想可以知道哈夫曼树的建立是一步到位的贪心法,即权重越大的结点越靠近该树的根,这样,出现频率越大的字符其编码就越短.但具体应该怎样建立起此N叉哈夫曼树呢?我们首先以N=2为例:S={A,B,C,D}W=[3,1,2,1]首先从W中选出两个最小权,1,1,将其删去,并以2(即1+1)替代W=[3,2,2];再从新的W中取出两个最小权,2,2,将其删去,并以4(即2+2)替代W=[3,4];依此类推,直到W中只一个值时合并结束,此时W=[7]以上两两合并的过程即为二叉哈夫曼树的建立过程,每一次的合并即是将两棵子树归于一个根结点下,于是可以建立二叉树如下: m0åæ1mmA0åæ1mmC0åæ1mmBD MIN-WPL=3*1+1*3+2*2+1*3=13 从某一根结点出发走向其左子树标记为0,走向其右子树标记为1,则可以得到以下编码A,B,C,D对应的编码为A:0B:110C:10D:111
N=3时又是怎样一种情况呢?设S={A,B,C,D,E}W=[7,4,2,5,3}则按权重排序可得S={D,B,E,C,A}W=[7,5,4,3,2]那么此哈夫曼树的树形应为怎样呢?是以下的左图,还是右图,或是两者均不是mmåâæåæmmllmåæåæCAåælllllmADBEDåæ
lmBåællEC 显然,要带权路径长WPL最短,那么,此树的高度就应尽可能的小,由此可知将此树建成丰满N叉树是最合理的,于是我们尽量使树每一层都为N个分枝.对于这道题的情况,我们具体来分析.按照哈夫曼树的思想,首先从W中取出权最小的三个值,即2,3,4,并以9(2+3+4)来代替,得到新的W=[9,7,5];再将这三个值合并成9+7+5=21这个结点.于是得到三叉哈夫曼树如下:måâællmDBåâælllECAWPL=1*7+1*5+2*2+2*3+2*4=30以0..N-1依次标记每个根结点的N个分枝,则可以得到每个字符相对应的编码:A:22B:1C:21D:0E:20我们发现对于这种情况恰巧每层均为N个分枝,但事实上并非所有的N叉哈夫曼树都可得到每层N个分枝.例于当N=3,‖S‖=6时就不可能构成一棵每层都为三个分枝的三叉树.如何来处理这种情况呢?最简单的处理方式就是添加若干出现概率为0的空字符填补在N叉树的最下一层,这些权为0的虚结点并无实际意义但却非常方全便于这棵N叉树的建立.空字符的添加个数add的计算如下:Y=‖S‖mod(n-1)add=0(Y=1)add=1(Y=0)add=N-Y(Y>1) 虚结点的加入使得权重最小的N-add个字符构成了距根结点最远的分枝,使其它字符构成的N叉树保持了丰满的N叉结构.例:N=3S={A,B,C,D,E,F}W=[1,2,3,4,5,6}则y:=6mod(3-1)=0add=1于是构成N叉树如下:­为虚结点¡åâællmFEåâællmDCåâæBA­WPL=1*6+1*5+2*4+2*3+3*2+3*1+3*0=33对应编码为:A:221B:220C:21D:20E:1F:0

❷ 请描述哈夫曼算法,并用图描述构造哈夫曼树的过程。

这个讲的相当清楚。
首先介绍什么是哈夫曼树。哈夫曼树又称最优二叉树,是一种带权路径长度最短的二叉树。所谓树的带权路径长度,就是树中所有的叶结点的权值乘上其到根结点的路径长度(若根结点为0层,叶结点到根结点的路径长度为叶结点的层数)。树的带权路径长度记为WPL=(W1*L1+W2*L2+W3*L3+...+Wn*Ln),N个权值Wi(i=1,2,...n)构成一棵有N个叶结点的二叉树,相应的叶结点的路径长度为Li(i=1,2,...n)。可以证明哈夫曼树的WPL是最小的。
哈夫曼在上世纪五十年代初就提出这种编码时,根据字符出现的概率来构造平均长度最短的编码。它是一种变长的编码。在编码中,若各码字长度严格按照码字所对应符号出现概率的大小的逆序排列,则编码的平均长度是最小的。(注:码字即为符号经哈夫曼编码后得到的编码,其长度是因符号出现的概率而不同,所以说哈夫曼编码是变长的编码。)
然而怎样构造一棵哈夫曼树呢?最具有一般规律的构造方法就是哈夫曼算法。一般的数据结构的书中都可以找到其描述:
一、对给定的n个权值{W1,W2,W3,...,Wi,...,Wn}构成n棵二叉树的初始集合F={T1,T2,T3,...,Ti,...,Tn},其中每棵二叉树Ti中只有一个权值为Wi的根结点,它的左右子树均为空。(为方便在计算机上实现算法,一般还要求以Ti的权值Wi的升序排列。)
二、在F中选取两棵根结点权值最小的树作为新构造的二叉树的左右子树,新二叉树的根结点的权值为其左右子树的根结点的权值之和。
三、从F中删除这两棵树,并把这棵新的二叉树同样以升序排列加入到集合F中。
四、重复二和三两步,直到集合F中只有一棵二叉树为止。
用C语言实现上述算法,可用静态的二叉树或动态的二叉树。若用动态的二叉树可用以下数据结构: struct tree{
float weight; /*权值*/
union{
char leaf; /*叶结点信息字符*/
struct tree *left; /*树的左结点*/
};
struct tree *right; /*树的右结点*/
};
struct forest{ /*F集合,以链表形式表示*/
struct tree *ti; /* F中的树*/
struct forest *next; /* 下一个结点*/
};
例:若字母A,B,Z,C出现的概率为:0.75,0.54,0.28,0.43;则相应的权值为:75,54,28,43。
构造好哈夫曼树后,就可根据哈夫曼树进行编码。例如:上面的字符根据其出现的概率作为权值构造一棵哈夫曼树后,经哈夫曼编码得到的对应的码值。只要使用同一棵哈夫曼树,就可把编码还原成原来那组字符。显然哈夫曼编码是前缀编码,即任一个字符的编码都不是另一个字符的编码的前缀,否则,编码就不能进行翻译。例如:a,b,c,d的编码为:0,10,101,11,对于编码串:1010就可翻译为bb或ca,因为b的编码是c的编码的前缀。刚才进行哈夫曼编码的规则是从根结点到叶结点(包含原信息)的路径,向左孩子前进编码为0,向右孩子前进编码为1,当然你也可以反过来规定。
这种编码方法是静态的哈夫曼编码,它对需要编码的数据进行两遍扫描:第一遍统计原数据中各字符出现的频率,利用得到的频率值创建哈夫曼树,并必须把树的信息保存起来,即把字符0-255(2^8=256)的频率值以2-4BYTES的长度顺序存储起来,(用4Bytes的长度存储频率值,频率值的表示范围为0--2^32-1,这已足够表示大文件中字符出现的频率了)以便解压时创建同样的哈夫曼树进行解压;第二遍则根据第一遍扫描得到的哈夫曼树进行编码,并把编码后得到的码字存储起来。 静态哈夫曼编码方法有一些缺点:一、对于过短的文件进行编码的意义不大,因为光以4BYTES的长度存储哈夫曼树的信息就需1024Bytes的存储空间;二、进行哈夫曼编码,存储编码信息时,若用与通讯网络,就会引起较大的延时;三、对较大的文件进行编码时,频繁的磁盘读写访问会降低数据编码的速度。
因此,后来有人提出了一种动态的哈夫曼编码方法。动态哈夫曼编码使用一棵动态变化的哈夫曼树,对第t+1个字符的编码是根据原始数据中前t个字符得到的哈夫曼树来进行的,编码和解码使用相同的初始哈夫曼树,每处理完一个字符,编码和解码使用相同的方法修改哈夫曼树,所以没有必要为解码而保存哈夫曼树的信息。编码和解码一个字符所需的时间与该字符的编码长度成正比,所以动态哈夫曼编码可实时进行。动态哈夫曼编码比静态哈夫曼编码复杂的多,有兴趣的读者可参考有关数据结构与算法的书籍。
前面提到的JPEG中用到了哈夫曼编码,并不是说JPEG就只用哈夫曼编码就可以了,而是一幅图片经过多个步骤后得到它的一列数值,对这些数值进行哈夫曼编码,以便存储或传输。哈夫曼编码方法比较易懂,大家可以根据它的编码方法,自己编写哈夫曼编码和解码的程序。

❸ 最优二叉树算法的基本概念

最优二叉树,也称哈夫曼(Haffman)树,是指对于一组带有确定权值的叶结点,构造的具有最小带权路径长度的二叉树。
那么什么是二叉树的带权路径长度呢?
在前面我们介绍过路径和结点的路径长度的概念,而二叉树的路径长度则是指由根结点到所有叶结点的路径长度之和。如果二叉树中的叶结点都具有一定的权值,则可将这一概念加以推广。设二叉树具有n个带权值的叶结点,那么从根结点到各个叶结点的路径长度与相应结点权值的乘积之和叫做二叉树的带权路径长度,记为:
WPL= Wk·Lk
其中Wk为第k个叶结点的权值,Lk 为第k个叶结点的路径长度。如图7.2所示的二叉树,它的带权路径长度值WPL=2×2+4×2+5×2+3×2=28。
在给定一组具有确定权值的叶结点,可以构造出不同的带权二叉树。例如,给出4个叶结点,设其权值分别为1,3,5,7,我们可以构造出形状不同的多个二叉树。这些形状不同的二叉树的带权路径长度将各不相同。图7.3给出了其中5个不同形状的二叉树。
这五棵树的带权路径长度分别为:
(a)WPL=1×2+3×2+5×2+7×2=32
(b)WPL=1×3+3×3+5×2+7×1=29
(c)WPL=1×2+3×3+5×3+7×1=33
(d)WPL=7×3+5×3+3×2+1×1=43
(e)WPL=7×1+5×2+3×3+1×3=29
最优二叉树算法 最优二叉树算法
由此可见,由相同权值的一组叶子结点所构成的二叉树有不同的形态和不同的带权路径长度,那么如何找到带权路径长度最小的二叉树(即哈夫曼树)呢?根据哈夫曼树的定义,一棵二叉树要使其WPL值最小,必须使权值越大的叶结点越靠近根结点,而权值越小的叶结点越远离根结点。
哈夫曼(Haffman)依据这一特点于1952年提出了一种方法,这种方法的基本思想是:
(1)由给定的n个权值{W1,W2,…,Wn}构造n棵只有一个叶结点的二叉树,从而得到一个二叉树的集合F={T1,T2,…,Tn};
(2)在F中选取根结点的权值最小和次小的两棵二叉树作为左、右子树构造一棵新的二叉树,这棵新的二叉树根结点的权值为其左、右子树根结点权值之和;
(3)在集合F中删除作为左、右子树的两棵二叉树,并将新建立的二叉树加入到集合F中;
(4)重复(2)(3)两步,当F中只剩下一棵二叉树时,这棵二叉树便是所要建立的哈夫曼树。

❹ 给定权3,4,5,6,7,8,9,试用算法构造一棵最优二叉树,画出这棵树并计算出...

建树步骤:
3
4
5
6
7
8
9
7
5
6
7
8
9
7
11
7
8
9
11
14
8
9
11
14
17
25
17
42
建立后的最优二叉树是这样滴:(线和箭头自己连一下吧汗~)
42
25
17
11
14
8
9
5
6
7
7
3
4
权(WPL):3*4+4*4+5*3+6*3+7*3+8*2+9*2=116

❺ 计算哈夫曼编码

六个权值(频率)是0.040.060.130.250.280.33

(1)从小到大排序0.040.060.130.250.280.33(这是有序序列)
(2)每次提取最小的两个结点,取结点0.04和结点0.06,组成新结点N0.10,其权值=0.04+0.06=0.10,
取数值较小的结点作为左分支,结点0.04为左分支,结点0.06为右分支.
(3)将新结点N0.10放入有序序列,保持从小到大排序:
N0.100.130.250.280.33
(4)重复步骤(2),提取最小的两个结点,N0.10与结点0.13组成新结点N0.23,其权值=0.10+0.13=0.23,
N0.10的数值较小,作为左分支,结点0.13就作为右分支.
(5)将新结点N0.23放入有序序列,保持从小到大排序:
N0.230.250.280.33
(6)重复步骤(2),提取最小的两个结点,N0.23与结点0.25组成新结点N0.48,其权值=0.23+0.25=0.48,
N0.23的数值较小,作为左分支,结点0.25就作为右分支.
(7)将新结点N0.48放入有序序列,保持从小到大排序:
0.280.33N0.48
(8)重复步骤(2),提取最小的两个结点,结点0.28与结点0.33组成新结点N0.61,其权值=0.28+0.33=0.61,
结点0.28的数值较小,作为左分支,结点0.33就作为右分支.
(9)将新结点N0.61放入有序序列,保持从小到大排序:
N0.48N0.61
(10)重复步骤(2),提取剩下的两个结点,N0.48与N0.61组成新结点N1.09,其权值=0.48+0.61=1.09,
数值较小的N0.48作为左分支,N0.61就作为右分支.
有序序列已经没有结点,得到"哈夫曼树":

N1.09
/
N0.48N0.61
//
N0.230.250.280.33
/
N0.100.13
/
0.040.06

带权路径长度(WPL):
根结点N1.09到结点0.33的路径长度是2,结点0.33的带权路径长度是0.33*2
根结点N1.09到结点0.28的路径长度是2,结点0.28的带权路径长度是0.28*2
根结点N1.09到结点0.25的路径长度是2,结点0.25的带权路径长度是0.25*2
根结点N1.09到结点0.13的路径长度是3,结点0.13的带权路径长度是0.13*3
根结点N1.09到结点0.06的路径长度是4,结点0.06的带权路径长度是0.06*4
根结点N1.09到结点0.04的路径长度是4,结点0.04的带权路径长度是0.04*4
所以,哈夫曼树的带权路径长度(WPL)等于
0.33*2+0.28*2+0.25*2+0.13*3+0.06*4+0.04*4=2.51

哈夫曼编码:
规定哈夫曼树的左分支代表0,右分支代表1.
从根结点N1.09到结点0.33,先后经历两次右分支,结点0.33的编码就是11
从根结点N1.09到结点0.28,先经历右分支,后经历左分支,结点0.28的编码就是10
从根结点N1.09到结点0.25,先经历左分支,后经历右分支,结点0.25的编码就是01
从根结点N1.09到结点0.13,先经历两次左分支,后经历右分支,结点0.13的编码就是001
从根结点N1.09到结点0.06,先经历三次左分支,后经历右分支,结点0.06的编码就是0001
从根结点N1.09到结点0.04,先后经历四次左分支,结点0.04的编码就是0000
得出所有结点的"哈夫曼编码":
字符f(频率0.33):11
字符e(频率0.28):10
字符d(频率0.25):01
字符c(频率0.13):001
字符b(频率0.06):0001
字符a(频率0.04):0000


//C语言测试程序(来自其他网友)
//
//输入构造哈夫曼树中带权叶子结点数(n):6
//输入6个整数作为权值:4613252833(将频率的小数形式改为整数形式)
//可以得出哈夫曼树的广义表形式,带权路径长度,以及哈夫曼编码.

#include<stdio.h>
#include<stdlib.h>
typedefintElemType;
structBTreeNode
{
ElemTypedata;
structBTreeNode*left;
structBTreeNode*right;
};

//1、输出二叉树,可在前序遍历的基础上修改。
//采用广义表格式,元素类型为int
voidPrintBTree_int(structBTreeNode*BT)
{
if(BT!=NULL)
{
printf("%d",BT->data);//输出根结点的值
if(BT->left!=NULL||BT->right!=NULL)
{
printf("(");
PrintBTree_int(BT->left);//输出左子树
if(BT->right!=NULL)
printf(",");
PrintBTree_int(BT->right);//输出右子树
printf(")");
}
}
}

//2、根据数组a中n个权值建立一棵哈夫曼树,返回树根指针
structBTreeNode*CreateHuffman(ElemTypea[],intn)
{
inti,j;
structBTreeNode**b,*q;
b=malloc(n*sizeof(structBTreeNode));
//初始化b指针数组,使每个指针元素指向a数组中对应的元素结点
for(i=0;i<n;i++)
{
b[i]=malloc(sizeof(structBTreeNode));
b[i]->data=a[i];
b[i]->left=b[i]->right=NULL;
}
for(i=1;i<n;i++)//进行n-1次循环建立哈夫曼树
{
//k1表示森林中具有最小权值的树根结点的下标,k2为次最小的下标
intk1=-1,k2;
//让k1初始指向森林中第一棵树,k2指向第二棵
for(j=0;j<n;j++)
{
if(b[j]!=NULL&&k1==-1)
{
k1=j;
continue;
}
if(b[j]!=NULL)
{
k2=j;
break;
}
}
//从当前森林中求出最小权值树和次最小
for(j=k2;j<n;j++)
{
if(b[j]!=NULL)
{
if(b[j]->data<b[k1]->data)
{
k2=k1;
k1=j;
}
elseif(b[j]->data<b[k2]->data)
k2=j;
}
}
//由最小权值树和次最小权值树建立一棵新树,q指向树根结点
q=malloc(sizeof(structBTreeNode));
q->data=b[k1]->data+b[k2]->data;
q->left=b[k1];
q->right=b[k2];

b[k1]=q;//将指向新树的指针赋给b指针数组中k1位置
b[k2]=NULL;//k2位置为空
}
free(b);//删除动态建立的数组b
returnq;//返回整个哈夫曼树的树根指针
}

//3、求哈夫曼树的带权路径长度
ElemTypeWeightPathLength(structBTreeNode*FBT,intlen)//len初始为0
{
if(FBT==NULL)//空树返回0
return0;
else
{
if(FBT->left==NULL&&FBT->right==NULL)//访问到叶子结点
{
printf("+%d*%d",FBT->data,len);
returnFBT->data*len;
}
else//访问到非叶子结点,进行递归调用,
{//返回左右子树的带权路径长度之和,len递增
returnWeightPathLength(FBT->left,len+1)+WeightPathLength(FBT->right,len+1);
}
}
}

//4、哈夫曼编码(可以根据哈夫曼树带权路径长度的算法基础上进行修改)
voidHuffManCoding(structBTreeNode*FBT,intlen)//len初始值为0
{
//定义静态数组a,保存每个叶子的编码,数组长度至少是树深度减一
staticinta[10];
inti;
//访问到叶子结点时输出其保存在数组a中的0和1序列编码
if(FBT!=NULL)
{
if(FBT->left==NULL&&FBT->right==NULL)
{
printf("权值为%d的编码:",FBT->data);
for(i=0;i<len;i++)
printf("%d",a[i]);
printf(" ");
}
else//访问到非叶子结点时分别向左右子树递归调用,
{//并把分支上的0、1编码保存到数组a的对应元素中,
//向下深入一层时len值增1
a[len]=0;
HuffManCoding(FBT->left,len+1);
a[len]=1;
HuffManCoding(FBT->right,len+1);
}
}
}

intmain()
{
intn,i;
ElemType*a;
structBTreeNode*fbt;
printf("输入构造哈夫曼树中带权叶子结点数(n):");
while(1)
{
scanf("%d",&n);
if(n>1)
break;
else
printf("重输n值:");
}
a=malloc(n*sizeof(ElemType));
printf("输入%d个整数作为权值:",n);
for(i=0;i<n;i++)
scanf("%d",&a[i]);
fbt=CreateHuffman(a,n);
printf("广义表形式的哈夫曼树:");
PrintBTree_int(fbt);
printf(" ");
printf("哈夫曼树的带权路径长度: ");
printf("=");
printf(" =%d ",WeightPathLength(fbt,0));
printf("树中每个叶子结点的哈夫曼编码: ");
HuffManCoding(fbt,0);

return0;
}

❻ 数据结构中什么是排序算法的稳定性

第一章 数据结构基本概念
1、基本概念:理解什么是数据、数据对象、数据元素、数据结构、数据的逻辑结构与物理结构、逻辑结构与物理结构间的关系。
2、面向对象概念:理解什么是数据类型、抽象数据类型、数据抽象和信息隐蔽原则。了解什么是面向对象。由于目前关于这个问题有许多说法,我们采用了一种最流行的说法,即Coad与Yourdon 给出的定义:面向对象 = 对象 + 类 + 继承 + 通信。
要点:
·抽象数据类型的封装性
·面向对象系统结构的稳定性
·面向对象方法着眼点在于应用问题所涉及的对象
3、数据结构的抽象层次:理解用对象类表示的各种数据结构
4、算法与算法分析:理解算法的定义、算法的特性、算法的时间代价、算法的空间代价。
要点:·算法与程序的不同之处需要从算法的特性来解释
·算法的正确性是最主要的要求
·算法的可读性是必须考虑的
·程序的程序步数的计算与算法的事前估计
·程序的时间代价是指算法的渐进时间复杂性度量

第二章 数组
1、作为抽象数据类型的数组:数组的定义、数组的按行顺序存储与按列顺序存储
要点:
·数组元素的存放地址计算
2、顺序表:顺序表的定义、搜索、插入与删除
要点:
·顺序表搜索算法、平均比较次数的计算
·插入与删除算法、平均移动次数的计算
3、多项式:多项式的定义
4、字符串:字符串的定义及其操作的实现
要点:
·串重载操作的定义与实现

第三章 链接表
1、单链表:单链表定义、相应操作的实现、单链表的游标类。
要点:
·单链表的两种定义方式(复合方式与嵌套方式)
·单链表的搜索算法与插入、删除算法
·单链表的递归与迭代算法
2、循环链表:单链表与循环链表的异同
3、双向链表:双向链表的搜索、插入与删除算法、链表带表头结点的优点
4、多项式的链接表示

第四章 栈与队列
1、栈:栈的特性、栈的基本运算
要点:
·栈的数组实现、栈的链表实现
·栈满及栈空条件、抽象数据类型中的先决条件与后置条件
2、栈的应用:用后缀表示计算表达式,中缀表示改后缀表示
3、队列:队列的特性、队列的基本运算
要点:
·队列的数组实现:循环队列中队头与队尾指针的表示,队满及队空条件
·队列的链表实现:链式队列中的队头与队尾指针的表示、
4、双向队列:双向队列的插入与删除算法
5、优先级队列:优先级队列的插入与删除算法

第五章 递归与广义表
1、递归:递归的定义、递归的数据结构、递归问题用递归过程求解
要点:·链表是递归的数据结构,可用递归过程求解有关链表的问题
2、递归实现时栈的应用
要点:·递归的分层(树形)表示:递归树
·递归深度(递归树的深度)与递归工作栈的关系
·单向递归与尾递归的迭代实现
3、广义表:广义表定义、广义表长度、广义表深度、广义表表头、广义表表尾
要点:
·用图形表示广义表的存储结构
·广义表的递归算法

第六章 树与森林
1、树:树的定义、树的基本运算
要点:
·树的分层定义是递归的
·树中结点个数与高度的关系
2、二叉树:二叉树定义、二叉树的基本运算
要点:
·二叉树性质、二叉树中结点个数与高度的关系、不同种类的二叉树棵数
·完全二叉树的顺序存储、完全二叉树的双亲、子女和兄弟的位置
·二叉树的前序·中序·后序·层次遍历
·前序
·中序
·后序的线索化二叉树、前驱与后继的查找方法
3、霍夫曼树:霍夫曼树的构造方法、霍夫曼编码、带权路径长度的计算
4、树的存储:树的广义表表示、树的双亲表示、树与二叉树的对应关系、树的先根·中根·后根·层次遍历。
5、堆:堆的定义、堆的插入与删除算法
要点:
·形成堆时用到的向下调整算法及形成堆时比较次数的上界估计
·堆插入时用到的向上调整算法

第七章 集合与搜索
1、集合的概念:集合的基本运算、集合的存储表示
要点:
·用位数组表示集合时集合基本运算的实现
·用有序链表表示集合时集合基本运算的实现
2、并查集:并查集定义、并查集的三种基本运算的实现
3、基本搜索方法
要点:
·对一般表的顺序搜索算法(包括有监视哨和没有监视哨)
·对有序顺序表的顺序搜索算法、用判定树(即扩充二叉搜索树)描述搜索,以及平均搜索长度(成功与不成功)的计算。
·对有序顺序表的折半搜索算法、用判定树(即扩充二叉搜索树)描述搜索,以及平均搜索长度(成功与不成功)的计算。
4、二叉搜索树:
要点:
·动态搜索树与静态搜索树的特性
·二叉搜索树的定义、二叉搜索树上的搜索算法、二叉搜索树搜索时的平均搜索长度(成功与不成功)的计算。
·AVL树结点上的平衡因子、AVL树的平衡旋转方法
·高度为h的AVL树上的最少结点个数与最多结点个数
· AVL树的搜索方法、插入与删除方法

第八章 图
1、图:图的定义与图的存储表示
要点:
·邻接矩阵表示(通常是稀疏矩阵)
·邻接表与逆邻接表表示
·邻接多重表(十字链表)表示
2、深度优先遍历与广度优先遍历
要点:
·生成树与生成树林的定义
·深度优先搜索是个递归的过程,而广度优先搜索是个非递归的过程
·为防止重复访问已经访问过的顶点,需要设置一个访问标志数组visited
3、图的连通性
要点:
·深度优先搜索可以遍历一个连通分量上的所有顶点
·对非连通图进行遍历,可以建立一个生成森林
·对强连通图进行遍历,可能建立一个生成森林
·关节点的计算和以最少的边构成重连通图
4、最小生成树
要点:
·对于连通网络、可用不会构成环路的权值最小的n-1条边构成最小生成树
·会画出用Kruskal算法及Prim算法构造最小生成树的过程
5、单源最短路径
要点:
·采用逐步求解的方式求某一顶点到其他顶点的最短路径
·要求每条边的权值必须大于零
6、活动网络
要点:
·拓扑排序、关键路径、关键活动、AOE网
·拓扑排序将一个偏序图转化为一个全序图。
·为实现拓扑排序,要建立一个栈,将所有入度为零的顶点进栈
·关键路径的计算

第九章 排序
1、基本概念:关键码、初始关键码排列、关键码比较次数、数据移动次数、稳定性、附加存储、内部排序、外部排序
2、插入排序:
要点:
·当待排序的关键码序列已经基本有序时,用直接插入排序最快
3、选择排序:
要点:
·用直接选择排序在一个待排序区间中选出最小的数据时,与区间第一个数据对调,而不是顺次后移。这导致方法不稳定。
·当在n个数据(n很大)中选出最小的5 ~ 8个数据时,锦标赛排序最快
·锦标赛排序的算法中将待排序的数据个数n补足到2的k次幂2k-1<n≤2k
·在堆排序中将待排序的数据组织成完全二叉树的顺序存储。
4、交换排序:
要点:
·快速排序是一个递归的排序方法
·当待排序关键码序列已经基本有序时,快速排序显着变慢。
5、二路归并排序:
要点:
·归并排序可以递归执行
·归并排序需要较多的附加存储。可以采用一种"推拉法"(参见教科书上习题)实现归并排序,算法的时间复杂度为O (n)、空间复杂度为O(1)
·归并排序对待排序关键码的初始排列不敏感,排序速度较稳定
6、外排序
要点:
·多路平衡归并排序的过程、I/O缓冲区个数的配置
·外排序的时间分析、利用败者树进行多路平衡归并
·利用置换选择方法生成不等长的初始归并段
·最佳归并树的构造及WPL的计算

第十章 索引与散列
1、线性索引:
要点:
·密集索引、稀疏索引、索引表计算
·基于属性查找建立倒排索引、单元式倒排表
2、动态搜索树
要点:
·平衡的m路搜索树的定义、搜索算法
·B树的定义、B树与平衡的m路搜索树的关系
·B树的插入(包括结点分裂)、删除(包括结点调整与合并)方法
·B树中结点个数与高度的关系
·B+树的定义、搜索、插入与删除的方法
3、散列表
要点:
·散列函数的比较
·装填因子 a 与平均搜索长度的关系,平均搜索长度与表长m及表中已有数据对象个数n的关系
·解决地址冲突的(闭散列)线性探查法的运用,平均探查次数的计算
·线性探查法的删除问题、散列表类的设计中必须为各地址设置三个状态
·线性探查法中的聚集问题
·解决地址冲突的(闭散列)双散列法的运用,平均探查次数的计算
·双散列法中再散列函数的设计要求与表长m互质,为此m设计为质数较宜
·解决地址冲突的(闭散列)二次散列法的运用,平均探查次数的计算
·注意:二次散列法中装填因子 a 与表长m的设置
·解决地址冲突的(开散列)链地址法的运用,平均探查次数的计算

❼ 哈夫曼树是什莫

哈夫曼树又称最优二叉树,是一种带权路径长度最短的二叉树。所谓树的带权路径长度,就是树中所有的叶结点的权值乘上其到根结点的路径长度(若根结点为0层,叶结点到根结点的路径长度为叶结点的层数)。树的路径长度是从树根到每一结点的路径长度之和,记为WPL=(W1*L1+W2*L2+W3*L3+...+Wn*Ln),N个权值Wi(i=1,2,...n)构成一棵有N个叶结点的二叉树,相应的叶结点的路径长度为Li(i=1,2,...n)。
例子:
17
/ \
8 9
/ \
3 6
/ \
1 2
另外,补充一下,构造哈夫曼树的主要目的是为了进行哈夫曼编码,是一种用于无损数据压缩的熵编码(权编码)算法。也称“霍夫曼编码”,“赫夫曼编码”。1952年,David A. Huffman在麻省理工攻读博士时所发明的,并发表于《一种构建极小多余编码的方法》(A Method for the Construction of Minimum-Rendancy Codes)一文。

❽ 两道题,求详细过程,讲解的。

首先声明,我没学过数据结构,以下专业术语不正确的或者做错了那么。。。请自己翻书查相关的准确术语
nk=(k-1)n0+1
如果nk成为父节点有nk个,n0成为子节点有n0个。对于k叉树而言,每当一个子节点拓展为一个父节点时,则子节点变为父节点即ak+=1同时a0-=1,同时子节点又多了k个即an+=k,两式子联立得每拓展一次时
ak+=1 a0+=k-1
又因为树的根节点是没有父亲的,所以n0要再加1
就得到上面的关系了。

自己画画图就出来了

第二题
树的形状如下图

○ 8
○ 7
○ 4
○ 3
1 2
中间的线不知道怎么画,就是A的子女分别是B和8,B的子女分别是C和7,下同,最后的E的子女是1和2
WPL算法 1*5+2*5+3*4+4*3+7*2+8*1 答案自己算(如果所有的路径的权都是1的话。。)

哈弗曼数算法如下
霍夫曼算法
(1)由给定的n个权值构造具有n棵扩充二叉树的森林F,其中每一棵扩充二叉树只有一个带有权值的根结点;
(2)在F中选取两棵根结点的权值最小的扩充二叉树作为左、右子树构造一棵新的二叉树,置新的二叉树的根结点的权值为其左、右子树上根结点的权值的之和。在F中删去这两棵二叉树,把新的二叉树加入F;
(3)重复步骤(2)直到F中仅剩下一棵树为止。

反正简单的理解就是说越是小的数越是放下面,然后每个根节点下面就放一个带有权的数,另一个当然就是根节点了,然后小的放下面,大的放上面,所谓WPL就是根节点到叶节点有几条路径,简单来说就是几条线,再乘以那个叶节点上的权值,然后都加起来就可以了。哈弗曼算法是这样的,怎么证明的忘记了。。。

❾ 用huffman算法求带权为2,3,5,7,8的最优2元树,要求画出中间过程

7/8应该一起作为同一父的叶这样才是最优,权为55

把最小的两个数2、3放在最下面作为左右叶子节点,得出他们的父节点权值5,然后它和剩余里最小的数5做成左右兄弟节点,得出父节点10,以此类推啊,10和7得出17,17和8,得到跟节点25完成。

例如:

先将所有的权值选出最小的两个值,为1,4,这两个的和为5,那么再从5,9,25,36,49中选出两个最小的,为5和9,然后再从14,25,36,49中选出两个最小的,为14,25,依次进行下去。那么就可以得到最优二叉树为:() / () 49 / () 36 / () 25 / () 9 / 1 4

(9)算法WPL扩展阅读:

所谓树的带权路径长度,就是树中所有的叶结点的权值乘上其到根结点的路径长度(若根结点为0层,叶结点到根结点的路径长度为叶结点的层数)。

树的路径长度是从树根到每一结点的路径长度之和,记为WPL=(W1*L1+W2*L2+W3*L3+...+Wn*Ln),N个权值Wi(i=1,2,...n)构成一棵有N个叶结点的二叉树,相应的叶结点的路径长度为Li(i=1,2,...n)。可以证明哈夫曼树的WPL是最小的。

热点内容
interbase数据库 发布:2025-05-14 13:49:50 浏览:691
微商海报源码 发布:2025-05-14 13:49:42 浏览:346
分布式缓存部署步骤 发布:2025-05-14 13:24:51 浏览:611
php获取上一月 发布:2025-05-14 13:22:52 浏览:90
购买云服务器并搭建自己网站 发布:2025-05-14 13:20:31 浏览:689
sqlserver建立视图 发布:2025-05-14 13:11:56 浏览:485
搭建httpsgit服务器搭建 发布:2025-05-14 13:09:47 浏览:256
新电脑拿回来我该怎么配置 发布:2025-05-14 13:09:45 浏览:241
视频服务器新建ftp用户 发布:2025-05-14 13:03:09 浏览:226
php花生 发布:2025-05-14 12:54:30 浏览:551