数据结构
线性表
笔记
【考纲内容】
-
1.线性表的基本概念
-
2.线性表的实现
- (1)顺序存储
- (2)链式存储
-
3.线性表的应用
【考情统计】
年份 | 单选题 | 综合题 | 总分值 | 考点 |
---|---|---|---|---|
2009 | 0 | 1 | 15 | 双指针遍历单链表 |
2010 | 0 | 1 | 13 | 倒置数组 |
2011 | 0 | 1 | 15 | 寻找数组中位数 |
2012 | 0 | 1 | 15 | 单链表遍历操作 |
2013 | 1 | 2 | 25 | 线性表的顺序表示、线性表的链式表示 |
2014 | 0 | 0 | 0 | 未考察 |
2015 | 0 | 1 | 15 | 单链表遍历操作 |
2016 | 2 | 0 | 4 | 单链表插入操作、双循环链表删除操作 |
2017 | 0 | 0 | 0 | 未考察 |
2018 | 0 | 1 | 13 | 数组最小为出现正整数 |
2019 | 1 | 1 | 13 | 倒置重排单链表 |
2020 | 0 | 1 | 15 | 三元组的最短距离 |
2021 | 1 | 0 | 2 | 单循环链表删除操作 |
2022 | 0 | 0 | 0 | 未考察 |
2023 | 1 | 0 | 2 | 双链表操作 |
【考点解读】
- 本章内容作为后一章节的基础,主要考查对算法操作的理解。要求考生熟练掌握线性表的结构,积累算法思想。考生需要牢记本章节中线性表的结构以及相应的各种操作。对于408算法题,在时间有限的情况下,需要对算法思想与代码可执行性进行取舍,算法思想具有更高的优先级,建议考生在算法题作答中将更多精力放在描述算法的思想与过程上。
【复习建议】
- 本章要注意理解和掌握各种线性表的结构与操作实现。主要掌握以下知识点:
- 1.掌握线性表的顺序存储和链式存储,以及各自的特点。
- 2.掌握顺序表各种操作的实现,理解时间复杂度的计算过程。
- 3.掌握各类链表的插入删除操作,理解时间复杂度的计算过程。
- 4.掌握链表的其他算法,如倒置链表、快慢指针法等,学会熟练运用。
- 5.本章出算法大题的概率很高,建议考生认真对待本书专项练习章节的习题。
线性表的基本概念
线性表的定义
-
①相同数据类型的数据元素;②有限;③序列。
-
线性表是具有相同数据类型的n(n≥0)个数据元素的有限序列,其中n为表长,当n=0时线性表是一个空表。若用L命名线性表,则其一般表示为
L = ( a 1 , a 2 , , a i , a m , , a n ) L=({a_1, a_2,, a_i, a_m,, a_n}) L=(a1,a2,,ai,am,,an)
式中,a1是唯一的“第一个”数据元素,又称表头元素;a是唯一的“最后一个”数据元素,又称表尾元素。除第一个元素外,每个元素有且仅有一个直接前驱。除最后一个元素外,每个元素仅有一个直接后继(“直接前驱”和“前驱”、“直接后继”和“后继”通常被视为同以上就是线性表的逻辑特性,这种线性有序的逻辑结构正是线性表名字的由来。
线性表特点
-
①个数有限:②逻辑上顺序:③相同数据类型;④抽象性。
-
表中元素的个数有限。
-
表中元素具有逻辑上的顺序性,表中元素有其先后次序。
-
表中元素都是数据元素,每个元素都是单个元素。
-
表中元素的数据类型都相同,这意味着每个元素占有相同大小的存储空间。
-
表中元素具有抽象性,即仅讨论元素间的逻辑关系,而不考虑元素究竟表示什么内容。
-
逻辑特性:除第1个元素外,每个元素有且仅有1个直接前驱;除最后一个元素外,每个元素有且仅有1个直接后继
-
线性表中元素的位序:从1开始
数组中元素的位序:从0开始
线性表长度
- 所含元素个数,用n表示,n为0→“空表"。
逻辑特性
- 除表头、表尾元素之外,其他元素只有一个直接前驱、直接后继。
存储结构
- 顺序表:连续空间。
- ①**随机访问**;
- ②占用连续存储空间,存储密度=1;
- ③插入、删除要移动多个元素;
- ④存储空间一次性分配。
- 链表:单链表、双链表、循环单链表、循环双链表、静态链表。
- ①**不支持随机访问**;
- ②结点存储空间利用率低(存储指针);
- ③支持存储空间动态分配
- ④**插入、删除无需移动元素**。
线性表的基本操作
- InitList(&L):初始化表。构造一个空的线性表,分配内存空间。
- Length(L):求表长。返回线性表L的长度,即L中数据元素的个数。
- LocateElem(L,e):按值查找操作。在表L中查找具有给定关键字值的元素。
- GetElem(L,i):按位查找操作。获取表L中第i个位置的元素的值。
- ListInsert(&L,i,e):插入操作。在表L中的第i个位置上插入指定元素e。
- ListDelete(&L,i,&e):删除。删除表L第i个位置的元素,用e返回删除元素的值。
- PrintList(L):输出操作。按前后顺序输出线性表L的所有元素值。
- Empty(L):判空操作。若L为空表,则返回true,否则返回false。
- DestroyList(&L):销毁操作。销毁线性表,并释放线性表L所占用的内存空间。
- 当操作对实际线性表L有改动的时候,需要用“&”把修改结果“带回来”。
线性表的实现:顺序存储
顺序表定义(逻辑结构)
(算法题)顺序表的应用(2010、2011、2018、2020)
-
用一组地址连续的存储单元依次存储线性表中的数据元素,使得逻辑上相邻的两个元素在物理位置上也相邻。
-
表(Sequential List)通常用数组来实现,指把线性表中的所有元素,按照其逻辑顺序次存储到计算机存储器的一块连续存储空间中。
-
顺序表:(物理结构)用顺序存储的方式,实现线性表的顺序存储。
即把逻辑上相邻的元素,存储在物理上也相邻的存储单元中,元素之间的关系由存储单元的邻接关系来体现。 :顺序表分得的内存空间一定是连续的
结点内容:每个结点只存储数据元素
逻辑结构:线性表
特点
-
地址连续,一次存储,随即存放,类型相同。
-
随机访问:即可以在 O(1) 时间内找到第 i 个元素(根据数组下标直接找);
存储密度高:每个结点只存储数据元素(链式存储需要消耗一定的空间存指针);
拓展容量不方便:即便采用动态分配的方式实现,拓展长度的时间复杂度也比较高;
插入、删除操作不方便:需要移动大量元素
顺序表基本操作
顺序表上操作的时间复杂度分析(2023)
-
①结构体定义
包括一个存储表中元素数组data[]和一个指示元素个数变量:length。
typedef struct{ int data[maxsize];//存放顺序表元素的数组 int length;//存放顺序表的长度 }Sqlist;//顺序表类型的定义
-
②初始化
将length设置为0:
L.length=0
-
③插入操作
L的第i个位置插入新元素e,先判断位置是否合法,将第1个元素及其后所有元素依次往后移动一个位置,空位置插入新元素e,顺序表长度增加1,先后移,再放入,从后往前。(否则会覆盖)
for(intj=L.length;j>=1;j-) //将第1个元素及之后的元素后移 L.data[j]=L.data[j-1]; L.data[i-1]= e;//在位置i处放入e L.length+;//线性表长度加1
时间复杂度:O(n)
-
最好情况:在表尾插入(即i=n+1),元素后移语句将不执行,时间复杂度为O(1)
-
最坏情况:在表头插入(即i=1),元素后移语句将执行n次,时间复杂度为O(n)
-
平均情况:假设
p i ( p i = 1 n + 1 ) p_i(p_i=\frac1{n+1}) pi(pi=n+1
-