自学考试数据结构重点总结02331整理.docx
- 文档编号:26549143
- 上传时间:2023-06-20
- 格式:DOCX
- 页数:39
- 大小:1.34MB
自学考试数据结构重点总结02331整理.docx
《自学考试数据结构重点总结02331整理.docx》由会员分享,可在线阅读,更多相关《自学考试数据结构重点总结02331整理.docx(39页珍藏版)》请在冰豆网上搜索。
自学考试数据结构重点总结02331整理
自考数据构造重点(整顿)
第一章概论
1.瑞士计算机科学家沃思提出:
算法+数据构造=程序。
算法是对数据运算描述,而数据构造涉及逻辑构造和存储构造。
由此可见,程序设计实质是针对实际问题选取一种好数据构造和设计一种好算法,而好算法在很大限度上取决于描述实际问题数据构造。
2.数据是信息载体。
数据元素是数据基本单位。
一种数据元素可以由若干个数据项构成,数据项是具备独立含义最小标记单位。
数据对象是具备相似性质数据元素集合。
3.数据构造指是数据元素之间互有关系,即数据组织形式。
数据构造普通涉及如下三方面内容:
数据逻辑构造、数据存储构造、数据运算
①数据逻辑构造是从逻辑关系上描述数据,与数据元素存储构造无关,是独立于计算机。
数据逻辑构造分类:
线性构造和非线性构造
②数据元素及其关系在计算机内存储方式,称为数据存储构造(物理构造)。
数据存储构造是逻辑构造用计算机语言实现,它依赖于计算机语言。
③数据运算。
最惯用检索、插入、删除、更新、排序等。
4.数据四种基本存储办法:
顺序存储、链接存储、索引存储、散列存储
(1)顺序存储:
普通借助程序设计语言数组描述。
(2)链接存储:
普通借助于程序语言指针来描述。
(3)索引存储:
索引表由若干索引项构成。
核心字是能唯一标记一种元素一种或各种数据项组合。
(4)散列存储:
该办法基本思想是:
依照元素核心字直接计算出该元素存储地址。
5.算法必要满足5个准则:
输入,0个或各种数据作为输入;输出,产生一种或各种输出;有穷性,算法执行有限步后结束;拟定性,每一条指令含义都明确;可行性,算法是可行。
算法与程序区别:
程序必要依赖于计算机程序语言,而一种算法可用自然语言、计算机程序语言、数学语言或商定符号语言来描述。
当前惯用描述算法语言有两类:
类Pascal和类C。
6.评价算法优劣:
算法"对的性"是一方面要考虑。
此外,重要考虑如下三点:
①执行算法所耗费时间,即时间复杂性;
②执行算法所耗费存储空间,重要是辅助空间,即空间复杂性;
③算法应易于理解、易于编程,易于调试等,即可读性和可操作性。
以上几点最重要是时间复杂性,时间复杂度惯用渐进时间复杂度表达。
7.算法求解问题输入量称为问题规模,用一种正整数n表达。
8.常用时间复杂度按数量级递增排列依次为:
常数阶0
(1)、对数阶0(log2n)、线性阶0(n)、线性对数阶0(nlog2n)、平方阶0(n2)立方阶0(n3)、…、k次方阶0(nk)、指数阶0(2n)和阶乘阶0(n!
)。
9.一种算法空间复杂度S(n)定义为该算法所耗费存储空间,它是问题规模n函数,它涉及存储算法自身所占存储空间、算法输入输出数据所占存储空间和算法在运营过程中暂时占用存储空间。
第二章线性表
1.数据运算是定义在逻辑构造上,而运算详细实现是在存储构造上进行。
2.只要拟定了线性表存储起始位置,线性表中任意一种元素都可随机存取,因此顺序表是一种随机存取构造。
3.常用线性表基本运算:
(1)置空表InitList(L)构造一种空线性表L。
(2)求表长ListLength(L)求线性表L中结点个数,即求表长。
(3)GetNode(L,i)取线性表L中第i个元素。
(4)LocateNode(L,x)在L中查找第一种值为x元素,并返回该元素在L中位置。
若L中没有元素值为x,则返回0值。
(5)InsertList(L,i,x)在线性表L第i个元素之前插入一种值为x新元素,表L长度加1。
(6)DeleteList(L,i)删除线性表L第i个元素,删除后表L长度减1。
4.顺序存储办法:
把线性表数据元素按逻辑顺序依次存储在一组地址持续存储单元里办法。
顺序表(SequentialList):
用顺序存储办法存储线性表称为顺序表。
顺序表是一种随机存取构造,顺序表特点是逻辑上相邻结点其物理位置亦相邻。
5.顺序表上实现基本运算:
(1)插入:
该算法平均时间复杂度是O(n),即在顺序表上进行插入运算,平均要移动一半结点(n/2)。
(2)删除:
顺序表上做删除运算,平均要移动表中约一半结点(n-1)/2,平均时间复杂度也是O(n)。
6.采用链式存储构造可以避免频繁移动大量元素。
一种单链表可由头指针唯一拟定,因而单链表可以用头指针名字来命名。
①生成结点变量原则函数 p=(ListNode*)malloc(sizeof(ListNode));//函数malloc分派一种类型为ListNode结点变量空间,并将其首地址放入指针变量p中②释放结点变量空间原则函数free(p);//释放p所指结点变量空间③结点分量访问 办法二:
p-﹥data和p-﹥next
④指针变量p和结点变量*p关系:
指针变量p值——结点地址,结点变量*p值——结点内容
7.建立单链表:
(1)头插法建表:
算法:
p=(ListNode*)malloc(sizeof(ListNode));①//生成新结点
p->data=ch; ②//将读入数据放入新结点数据域中
p->next=head;③
head=p;④
(2)尾插法建表:
算法:
p=(ListNode*)malloc(sizeof(ListNode));①//生成新结点
p->data=ch; ②//将读入数据放入新结点数据域中
if(head==NULL)
head=p;//新结点插入空表
else
rear->next=p;③//将新结点插到*r之后
rear=p;④//尾指针指向新表尾
(3)尾插法建带头结点单链表:
头结点及作用:
头结点是在链表开始结点之前附加一种结点。
它具备两个长处:
⒈由于开始结点位置被存储在头结点指针域中,因此在链表第一种位置上操作就和在表其他位置上操作一致,不必进行特殊解决;
⒉无论链表与否为空,其头指针都是指向头结点非空指针(空表中头结点指针域空),因而空表和非空表解决也就统一了。
头结点数据域阴影表达该某些不存储信息。
在有应用中可用于存储表长等附加信息。
详细算法:
r=head; // 尾指针初值也指向头结点
while((ch=getchar())!
='\n'){
s=(ListNode*)malloc(sizeof(ListNode));//生成新结点
s->data=ch; //将读入数据放入新结点数据域中
r->next=s;
r=s;
}
r->next=NULL;//终端结点指针域置空,或空表头结点指针域置空
以上三个算法时间复杂度均为O(n)。
8.单链表上查找:
(带头结点)
(1)按结点序号查找:
序号为0是头结点。
算法:
p=head;j=0;//从头结点开始扫描
while(p->next&&jnext为NULL或i=j为止
p=p->next;
j++;
}
if(i==j)
returnp;//找到了第i个结点
elsereturnNULL;//当i<0或i>0时,找不到第i个结点
时间复杂度:
在等概率假设下,平均时间复杂度为:
为n/2=O(n)
(2)按结点值查找:
详细算法:
ListNode*p=head->next;//从开始结点比较。
表非空,p初始值指向开始结点
while(p&&p->data!
=key)//直到p为NULL或p->data为key为止
p=p->next;//扫描下一结点
returnp;//若p=NULL,则查找失败,否则p指向值为key结点
时间复杂度为:
O(n)
9.插入运算:
插入运算是将值为x新结点插入到表第i个结点位置上,即插入到ai-1与ai之间。
s=(ListNode*)malloc(sizeof(ListNode));②
s->data=x;③s->next=p->next④;p->next=s;⑤
算法时间重要耗费在查找结点上,故时间复杂度亦为O(n)。
10.删除运算
r=p->next;②//使r指向被删除结点ai
p->next=r->next③;//将ai从链上摘下
free(r);④//释放结点ai空间给存储池
算法时间复杂度也是O(n)。
p指向被删除前一种结点。
链表上实现插入和删除运算,不必移动结点,仅需修改指针。
11.单循环链表—在单链表中,将终端结点指针域NULL改为指向表头结点或开始结点即可。
判断空链表条件是head==head->next;
12.仅设尾指针单循环链表:
用尾指针rear表达单循环链表对开始结点a1和终端结点an查找时间都是O
(1)。
而表操作经常是在表首尾位置上进行,因而,实用中多采用尾指针表达单循环链表。
判断空链表条件为rear==rear->next;
13.循环链表:
循环链表特点是不必增长存储量,仅对表链接方式稍作变化,即可使得表解决更加以便灵活。
若在尾指针表达单循环链表上实现,则只需修改指针,不必遍历,其执行时间是O
(1)。
详细算法:
LinkListConnect(LinkListA,LinkListB) {//假设A,B为非空循环链表尾指针
LinkListp=A->next;//①保存A表头结点位置
A->next=B->next->next;//②B表开始结点链接到A表尾
free(B->next);//③释放B表头结点
B->next=p;//④
returnB;//返回新循环链表尾指针
循环链表中没有NULL指针。
涉及遍历操作时,其终结条件就不再是像非循环链表那样鉴别p或p->next与否为空,而是鉴别它们与否等于某一指定指针,如头指针或尾指针等。
在单链表中,从一已知结点出发,只能访问到该结点及其后续结点,无法找到该结点之前其他结点。
而在单循环链表中,从任一结点出发都可访问到表中所有结点,这一长处使某些运算在单循环链表上易于实现。
14.双向链表:
双(向)链表中有两条方向不同链,即每个结点中除next域存储后继结点地址外,还增长一种指向其直接前趋指针域prior。
①双链表由头指针head惟一拟定。
②带头结点双链表某些运算变得以便。
③将头结点和尾结点链接起来,为双(向)循环链表。
15.双向链表前插和删除本结点操作
①双链表前插操作
voidDInsertBefore(DListNode*p,DataTypex){//在带头结点双链表中,将值为x新结点插入*p之前,设p≠NULL
DListNode*s=malloc(sizeof(DListNode));//①
s->data=x;//②
s->prior=p->prior;//③
s->next=p;//④
p->prior->next=s;//⑤
p->prior=s;//⑥
}
②双链表上删除结点*p自身操作
voidDDeleteNode(DListNode*p)
{//在带头结点双链表中,删除结点*p,设*p为非终端结点
p->prior->next=p->next;//①
p->next->prior=p->prior;//②
free(p);//③
}
与单链表上插入和删除操作不同是,在双链表中插入和删除必要同步修改两个方向上指针。
上述两个算法时间复杂度均为O
(1)。
16.顺序表和链表比较
时间性能:
a、线性表:
经常性查找;b、链式存储构造:
经常插入删除操作;
空间性能:
a、对数据量大小事先可以懂得用线性表;b、数据量变化较大用链式存储构造。
存储密度越大,存储空间运用率越高。
显然,顺序表存储密度是1,链表存储密度必定不大于1。
第三章栈和队列
1.栈称为后进先出(LastInFirstOut)线性表,简称为LIFO表。
栈是运算受限线性表,顺序栈也是用数组表达。
进栈操作:
进栈时,需要将S->top加1,①S->top==StackSize-1表达栈满
②"上溢"现象--当栈满时,再做进栈运算产生空间溢浮现象。
退栈操作:
退栈时,需将S->top减1,①S->top<0表达空栈
②"下溢"现象--当栈空时,做退栈运算产生溢浮现象。
下溢是正常现象,惯用作程序控制转移条件。
空栈时栈顶指针不能是0,只能是-1。
当程序中同步使用两个栈时,可以将两个栈栈底分别设在顺序存储空间两端,让两个栈顶各自向中间延伸。
当一种栈中元素较多而栈使用空间超过共享空间一半时,只要另一种栈元素不多,那么前者就可以占用后者某些存储空间。
当Top1=Top2-1时,栈满
2.为了克服顺序存储分派固定空间所产生溢出和空间挥霍问题。
可采用链式存储构造来存储栈。
链栈是没有附加头结点运算受限单链表。
栈顶指针就是链表头指针。
链栈中结点是动态分派,因此可以不考虑上溢,不必定义StackFull运算
栈一种重要应用是实现递归,直接调用自己或间接调用自己函数。
3.容许删除一端称为队头(Front),容许插入一端称为队尾(Rear),当队列中没有元素时称为空队列,队列亦称作先进先出(FirstInFirstOut)线性表,简称为FIFO表。
队列顺序存储构造称为顺序队列,顺序队列事实上是一种受限线性表。
顺序队列基本操作
①入队时:
将新元素插入rear所指位置,然后将rear加1。
②出队时:
删去front所指元素,然后将front加1并返回被删元素。
当头尾指针相等时,队列为空。
在非空队列里,头指针始终指向队头元素,而队尾指针始终指向队尾元素下一位置。
而栈顶指针指向栈顶元素。
4.循环队列:
为充分运用数组空间,克服上溢,可将数组空间想象为一种环状空间,并称这种环状数组表达队列为循环队列。
循环队列中进行出队、入队操作时,头尾指针仍要加1,朝前移动。
只但是当头尾指针指向向量上界(QueueSize-1)时,其加1操作成果是指向向量下界0。
这种循环意义下加1操作可以描述为:
①办法一:
if(i+1==QueueSize)//i表达front或rear
i=0;
else
i++;
②办法二--运用"模运算"
i=(i+1)%QueueSize;
循环队列中,由于入队时尾指针向前追赶头指针;出队时头指针向前追赶尾指针,导致队空和队满时头尾指针均相等。
因而,无法通过条件Q.front==Q.rear来鉴别队列是"空"还是"满"。
解决这个问题办法至少有三种:
①另设一种标志位以区别队列是空还是满;
②设立一种计数器记录队列中元素总数(即队列长度)。
③少用一种元素空间。
商定入队前,测试尾指针在循环意义下加1后与否等于头指针,若相等则以为队列满即尾指针Q.rear所指单元始终为空。
5.循环队列基本运算:
①置队空:
Q->front=Q->rear=0;
②判队空:
returnQ->rear==Q->front;
③判队满:
return(Q->rear+1)%QueueSize==Q->front;
④入队Q->data[Q->rear]=x; //新元素插入队尾
Q->rear=(Q->rear+1)%QueueSize;
⑤出队temp=Q->data[Q->front];
Q->front=(Q->front+1)%QueueSize; //循环意义下头指针加1
returntemp;
⑥取队头元素returnQ->data[Q->front];
6.队列链式存储构造简称为链队列。
它是限制仅在表头删除和表尾插入单链表。
为了简化解决,在队头结点之前附加一种头结点,并设队头指针指向此结点。
链队列基本运算:
(带头结点)
(1)构造空队:
Q->rear=Q->front;Q->rear->next=NULL;
(2)判队空:
returnQ->rear==Q->front;
(3)入队:
QueueNode*p=(QueueNode*)malloc(sizeof(QueueNode));//申请新结点
p->data=x; p->next=NULL;
Q->rear->next=p; //*p链到原队尾结点后
Q->rear=p; //队尾指针指向新尾
(4)出队:
当队列长度不不大于1时,只需修改头结点指针,尾指针不变
s=Q->front->next;Q->front->next=s->next;
x=s->data;free(s);returnx;
当队列长度等于1时,不但要修改头结点指针,还要修改尾指针
s=Q->front->next;Q->front->next=NULL;Q->rear==Q->front;
x=s->data;free(s);returnx;
(5)取队头元素:
returnQ->front->next->data;由于有头结点,因此用了next
①和链栈类似,不必考虑判队满运算及上溢。
②在出队算法中,普通只需修改队头指针。
但当原队中只有一种结点时,该结点既是队头也是队尾,故删去此结点时亦需修改尾指针,且删去此结点后队列变空。
7.用计算机来解决计算算术表达式问题,一方面要解决问题是如何将人们习惯书写中缀表达式转换成后缀表达式。
第四章多维数组和广义表
1.数组顺序存储方式:
普通采用顺序存储办法表达数组。
(1)行优先顺序 a11,a12,…,a1n,a21,a22,…,a2n,……,am1,am2,…,amn
(2)列优先顺序 a11,a21,…,am1,a12,a22,…,am2,……,a1n,a2n,…,amn
Pascal和C语言是按行优先顺序存储,而Fortran语言是按列优先顺序存储。
2.为了节约存储空间,可以对矩阵中有许多值相似或值为零元素矩阵,采用压缩存储。
特殊矩阵是指相似值元素或零元素在矩阵中分布有一定规律。
常用有对称矩阵、三角矩阵。
(1)对称矩阵在一种n阶方阵A中,若元素满足下述性质:
aij=aji0≤i,j≤n-1
称为n阶对称矩阵,它元素是关于主对角线对称,因此只需要存储矩阵上三角或下三角元素即可,让两个对称元素共享一种存储空间。
矩阵元素aij和数组元素sa【k】之间关系是
k=i×(i+1)/2+ji≥j0≤k k=j×(j+1)/2+ii<j0≤k (2)三角矩阵: 以主对角线划分,三角矩阵有上三角和下三角两种。 上三角矩阵是指它下三角(不涉及主角线)中元素均为常数c或零;下三角矩阵主对角线上方均为常数c或零。 普通状况,三角矩阵常数c均为零。 三角矩阵压缩存储: 三角矩阵中重复元素c可共享一种存储空间,别的元素正好有n×(n+1)/2个,因而,三角矩阵可压缩存储在一维数组sa[n(n+1)/2+1]中,其中c存储在数组最后一种元素中。 三角矩阵压缩存储构造是随机存取构造。 3.稀疏矩阵: 设矩阵Amn中有s个非零元素,若s远远不大于矩阵元素总数,则称A为稀疏矩阵。 为了节约存储单元,可用压缩存储办法只存储非零元素。 由于非零元素分布普通是没有规律,因而在存储非零元素同步,还必要存储非零元素所在行、列位置,因此可用三元组(i,j,aij)来拟定非零元素。 稀疏矩阵进行压缩存储普通有两类办法: 顺序存储(三元组表)和链式存储(十字链表)。 稀疏矩阵压缩存储会失去随机存取功能。 4.广义表是线性表推广,又称列表。 广义表是n(n≥0)个元素a1,a2,…,ai,…,an有限序列。 其中ai或者是原子或者是一种广义表。 ①广义表通惯用圆括号括起来,用逗号分隔其中元素。 ②为了区别原子和广义表,书写时用大写字母表达广义表,用小写字母表达原子。 ③若广义表Ls非空(n≥1),则al是LS表头,别的元素构成表(a1,a2,…,an)称为Ls表尾。 ④广义表具备递归和共享性质 广义表深度: 一种表展开后所含括号层数称为广义表深度。 19.广义表是一种多层次线性构造,事实上这就是一种树形构造。 任何一种非空广义表表头可以是原子,也可以是子表,而其表尾必然是子表。 head=(a,b)=a,tail(a,b)=(b) 对非空表A和(y),也可继续分解。 注意: 广义表()和(())不同。 前者是长度为0空表,对其不能做求表头和表尾运算;而后者是长度为l由空表作元素广义表,可以分解得到表头和表尾均是空表()。 广义表是一种有层次非线性构造,普通采用链式存储构造,每个元素用一种结点表达,结点由3个域构成,其中一种是tag标志位,用来区别结点是原子还是子表,当tag为零时结点是子表,第二个域为slink,用以存储子表地址;当tag为1时结点是原子,第二个域为data,用以存储元素值。 第五章树和二叉树 1.树表达法: 最惯用是树形图表达法;尚有3种嵌套集合、凹形、广义表。 树构造基本术语 (1)结点度(Degree) 树中一种结点拥有子树数称为该结点度(Degree)。 一棵树度是指该树中结点最大度数。 度为零结点称为叶子(Leaf)或终端结点。 度不为零结点称分支结点或非终端结点。 除根结点之外分支结点统称为内部结点。 根结点又称为开始结点。 (2)①途径(path)若树中存在一种结点序列k1,k2,…,ki,使得ki是ki+1双亲(1≤i 一种结点祖先是从根结点到该结点途径上所通过所有结点,而一种结点子孙则是以该结点为根子树中所有结点。 结点层数(Level)从根起算: 根层数为1,别的结点层数等于其双亲结点层数加1。 双亲在同一层结点互为堂兄弟。 树中结点最大层数称为树高度(Height)或深度(Depth)。 若将树中每个结点各子树当作是从左到右有顺序(即不能互换),则称该树为有序树(OrderedTree);否则称为无序树(UnoderedTree)。 若不特别指明,普通讨论树都是有序树。 森林(Forest)
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 自学考试 数据结构 重点 总结 02331 整理
![提示](https://static.bdocx.com/images/bang_tan.gif)