数据结构教程 李春葆版 框架总结

数据结构

绪论

  • 基本概念
    • 数据:描述客观事物的bits
    • 数据元素:表中的一条记录
    • 数据项:表头
    • 数据对象:表
    • 数据结构:表的具体实现
  • 数据结构的概念
    1. 逻辑结构
      1. 集合
      2. 线性
      3. 非线性
    2. 物理结构
      1. 顺序存储
      2. 链式存储
      3. 索引存储
      4. 哈希存储
    3. 数据运算
      1. 运算描述
      2. 运算实现
  • 数据类型与抽象数据类型
  • 算法:
    • 算法特性:有穷,确定,可行,输入,输出
    • 算法度量:
      1. 时间复杂度:渐进时间复杂度,随着问题规模n的增大,算法执行时间的增长率
      2. 空间复杂度:算法执行过程中零食占用存储空间大小的度量
  • 数据结构+算法=程序

线性表

  • 逻辑结构
    • 逻辑特征:每个元素唯一前驱后继
  • 存储结构
    • 顺序表
      • 基本特征:随机存取
    • 链表
      • 单链表
      • 双链表
      • 循环链表
  • 有序表
    • 二路归并算法:两个序列逐个对比,合适的拿出来,索引++,循环往复
    • 快速排序算法:不断地划分两个区间,递归调用
    • 直接插入算法:不断的将无序区数据插入有序区
  • 基本算法题
    • 增删查改
    • 排序
    • 递归

栈和队列

    • 特点:先进先出
    • 存储结构
      • 顺序栈
      • 链栈
    • 栈的应用
      • 表达式求值
      • 递归算法转化非递归算法
      • 求解迷宫问题
  • 队列
    • 特点:先进后出
    • 队列存储结构
      • 顺序队
      • 链队
    • 特殊队列
      • 循环队列
      • 双端队列
    • 应用
      • 求解迷宫问题(求最短路径)
      • 图层次遍历的非递归算法

  • 串的特点
  • 串的存储结构
    • 顺序串
      • 存储方法
      • 基本运算
    • 链串
      • 存储方法
      • 基本运算
  • 串的模式匹配
    • bf算法
      • 目的:找出主串中模式串的位置
      • 接口:主串,模式串
      • 临时变量
        • i用来遍历主串
        • j用来遍历模式串
      • 运算流程
        • 遍历主串中,遍历模式串逐个对比,若不匹配则主串,模式串都回溯,若匹配则继续比对下一个直到模式串比对完,返回位置
    • kmp算法
      • 目的:找出主串中模式串的位置
      • 接口:主串,模式串
      • 临时变量
        • next[]数组用来保证主串不回溯,模式串部分回溯
        • i用来遍历主串
        • j用来遍历模式串
      • 运算流程
        • getNext(t)获取next数组子函数
          • 目的:获取next[]数组
          • 接口:模式串
          • 临时变量
            • j用来遍历模式串
            • k用来标记前缀后缀相同数目
          • 运算流程
            • 当tk==tj时,说明相同前后缀数目+1,j++;k++;next[j]=k;否则k=next[k],k回退继续对比。
        • 遍历主串中,遍历模式串逐个对比,对比成功就下一个,不成功就按照next数组进行回溯j=next[j],继续对比直到结束,若模式串遍历完那么返回索引
    • kmp改进算法
      • 求nextval[]数组
        • next数组的作用是回退,如果模式串回退到相同字符,等于无效回退,所以求nextval数组时,所有回退到相同字符情况产生连坐,他们的next值都是以第一个为准
        • 当tk==tj时,说明相同前后缀数目+1,j++;k++;准备赋值nextval,再次判断tk==tj,如果相等,那么nextval[j]=next[k];否则正常执行nextval[k]=k

递归

  • 递归相关概念
    • 递归定义
      • 直接递归(主要)
      • 间接递归
    • 何时使用递归
      • 定义是递归的
      • 数据结构是递归的
      • 问题的求解方法是递归的
    • 递归模型
      • 递归出口
      • 递归体
        • 小问题(基本逻辑)
        • 大问题和小问题的联系
    • 递归执行过程
  • 递归调用的实现
  • 递归算法的设计方法
    • 递归算法的设计步骤
      • 假设出合理的小问题(基本逻辑)
      • 建立小问题和大问题之间的递归关系
      • 设置递归出口
    • 基于递归数据结构递归算法设计
      • 正整数(基本逻辑是加法)
      • 单链表(基本逻辑是指针移动)
    • 基于递归求解方法递归算法设计
      • 迷宫问题(基本逻辑是试探一步)

数组

  • 数组
    • 数组的特点
    • 多维数组的存储结构
      • 以行序为主的存储结构
      • 以列序为主的存储结构
    • 特殊矩阵的压缩存储(掌握数列求和公式)(下标都从0开始)
      • 对称矩阵压缩存储
        • k=i(i+1)/2+j
      • 上(下)三角矩阵压缩存储
        • 上三角k=i(2n-i+1)/2+j-i
        • 下三角k=i(i+1)/2+j
        • k=n(n+1)/2
      • 对角矩阵(带宽为3)
        • k=2i+j
    • 稀疏矩阵
      • 定义特点
      • 存储结构
        • 三元组
          • 节点(行号,列好,值)
          • 三元组顺序表(行数,列数,节点数组)
        • 十字链表

树和二叉树

    • 定义相关术语
    • 逻辑表示法
      • 树型表示法
      • 括号表示法
    • 树的性质
      • 树节点数等于度数和+1
      • 度为m,高度为h的树最多有(m^h-1)/(m-1)个节点
      • 度为m,第i层的树最多有m^(i-1)个节点
      • 度为m,节点数为n树最小高度为:向上取整(log_m(n(m-1)+1))
      • 节点数为n树最大高度为n-m+1
    • 树的遍历方法
      • 先根遍历
      • 后根遍历
      • 层次遍历
    • 树的存储方法
      • 双亲存储结构(顺序存储)
      • 孩子链存储结构
      • 孩子兄弟链存储结构(类似二叉树)
  • 二叉树
    • 二叉树定义
    • 满二叉树和完全二叉树
    • 二叉树的性质
      • 叶子节点数等于双分支节点数+1:n0=n2 + 1
      • 非空二叉树i层最多有2^(i-1)个节点
      • 高度为h二叉树最多2^h-1
      • n个节点二叉树最低高度为:向上取整(log_2(n+1))
      • 完全二叉树性质
        • i<=n/2,编号为i为分支节点
        • n为奇数,n1=0,n偶数n1=1;关系到最后一个分支节点是否单孩
        • i的左孩子为2i,右孩子为2i+1
        • i的父母为向下取整i/2
    • 二叉树的存储结构
      • 二叉树顺序存储
      • 二叉树链式存储
    • 二叉树的遍历及其应用
      • 先序遍历
      • 中序遍历
      • 后序遍历
      • 层次遍历
    • 二叉树的构造
      • 先序+中序
      • 后序+中序
    • 线索二叉树
      • 二叉树线索化
      • 遍历线索二叉树
    • 哈夫曼树
      • 构造哈夫曼树
      • 生成哈夫曼编码
  • 二叉树与树
    • 二叉树与树森林的转换:兄弟孩子链

  • 图的定义和相关术语
  • 图的存储结构
    • 邻接矩阵
      • 邻接矩阵结点
        • n,e:顶点数,边数
        • 顶点数组
        • 边关系矩阵
      • 顶点结点
        • no 编号
        • inf 信息
    • 邻接表
      • 邻接表结点
        • 顶点数组
        • n,e:顶点数,边数
      • 顶点结点
        • firstarc 第一个边链结点
      • 边链结点
        • adjvex 编号
        • nextarc 下一个边链结点
        • inf 信息
    • 十字邻接表
    • 邻接多重表
  • 图的基本运算
  • 图的遍历
    • 深度优先(DFS)
      • 接口:adjGragh *G,int v(起始节点的编号)
      • 临时变量
        • 全局变量 visited[]保存是否遍历过的信息
        • arcNode *p遍历边结点
      • 运算流程
        • 循环+递归
        • 读取第v个结点,设置visited数组
        • 循环读取所有边链结点
          • 若边链结点没有被读取,递归DFS(G,p->adjvex)
    • 广度优先(BFS)
      • 接口:adjGragh *G,int v(起始节点的编号)
      • 临时变量
        • 全局变量 visited[]保存是否遍历过的信息
        • arcNode *p遍历边结点
        • sqQueue *qu队列,保存的是序号
        • int w 出队结点
      • 运算流程
        • 出队访问,进队所有邻接点
        • 读取第v个结点,进队v
        • 当队列不为空时循环
          • 出队w,访问w,设置visited[w]
          • 进队所有邻接点
            • p访问第一个邻接点
            • 当p不为空时循环所有边链
              • 进队未被访问的节点
    • 应用
  • 生成树和最小生成树
    • 普里姆算法prim:设定一个起始点,每次选距离最短的点
    • 克鲁斯卡尔算法:每次选一个不产生回环的边
  • 最短路径
    • 广度遍历算法(不带权)
    • 迪杰斯特拉算法(单源最短路径):每次确定一个点的最短路径(不适合含负权值)
      • S集合:确定的最短路径的点的集合
      • path[][]:点最短路径的前驱节点
      • dist[][]:两点之间的路径长度
    • 弗洛伊德算法(任意两点之间最短路径):每次添加一个中转节点,确定一个最短路径
      • A[][]:保存两点的距离
      • path[][]:点路径的前驱节点
  • 拓扑排序(AOV图)
    • 将所有没有前驱的节点遍历,并删除节点及其边
  • 关键路径:拓扑图中最大长度的路径(AOE图)
    • ve:事件(点)最早开始时间
    • vl:事件(点)最迟开始时间
    • e:活动(边)最早
    • l:活动(边)最迟
    • d:活动差值,为0的就是关键活动

查找

  • 查找的基本概念
    • 查找
    • 平均查找长度
  • 线性表的查找
    • 顺序查找
    • 二分查找
      • 构造判断树
    • 分块查找
  • 树表的查找
    • 二叉排序树
      • 插入:作为叶子节点插入
      • 删除:特殊情况同时存在左右子树,把左子树最大的节点提上来
      • 查找
    • 二叉平衡树
      • 最高高度h与节点数n的关系
        • h1=1,h2=2
        • hk=h_(k-2)+h_(k-1)+1
        • 前几个规律1,2,4,7,12,20
      • 插入
        • 作为叶子节点插入
        • 调整
          • LL,RR调整:失衡节点孩子上调
          • RL,LR调整:失衡节点孙子上调
      • 删除
        • 当作二叉排序树删除
        • 发现失衡后做调整LL,RR,RL,LR
      • 查找
    • B-树
      • 插入
        • 不超过界限直接插入
        • 超过,加入后排序,把中间关键字提出,加入父母节点,两边分裂,成为其孩子。若父母也溢出,重复操作
      • 删除
        • 非叶子关键字:借最大的孩子到非叶子节点,然后删除叶子上孩子关键字,转换到删除叶子关键字
        • 叶子关键字
          • 满足条件直接删
          • 不满足最低界限
            • 自己借父母,父母借兄弟
            • 兄弟都不够借,连同自己与兄弟拆父母的一个关键字合并
            • 如果父母都不够借,把父母看成叶子节点重复操作
      • 查找
    • B+树
      • 和B-树的区别
        • 关键字的数量n的范围
          • b-树,n的范围向上取整(m/2)-1到m-1
          • b+树,2/m到m
        • 子树数量
          • b-数,n+1棵子树
          • b+,n课一个关键字对应一个子树
        • 节点作用
          • b- 所有节点关键字不重复,关键字是存储地址
          • b+ 非叶子节点只是索引作用,叶子节点的关键字才是存储作用,包含所有节点,并且有两个指针,一个用来遍历树结构,一个用来遍历顺序结构
  • 哈希表的查找
    • 哈希函数的构造
      • 装填因子:n/m
      • 除留余数法:p是小于等于m的素数
    • 解决哈西冲突的方法
      • 开放定址法
        • 线性探测法
        • 平方探测法
      • 拉链法

内排序

  • 排序的基本概念
    • 稳定性
  • 插入排序:每次将无序区第一个插入有序区
    • 直接插入算法
      • 接口:无序数组A,数组长度n
      • 临时变量
        • i遍历整个序列代表代插入关键字,j遍历有序区,temp保存带插入无序关键字
      • 运算过程
        • 两层循环,一层循环整个序列,二层循环遍历有序区插入
        • 一层循环内,先判断a[i]与前一个是否无序,若无序那就排序,temp保存关键字,j=i-1,进入二层循环,从后向前找到合适位置,并后移关键字一位,然后temp放入
    • 折半插入算法:只是第二层循环用的是折半查找
        • 接口:无序数组A,数组长度n
      • 临时变量
        • i遍历整个序列,j用来实现后移插入,temp保存关键字,low,high,mid实现折半查找
      • 运算过程
        • 两层循环,一层循环整个序列,二层有两个子循环,一子循环为折半查找,二子循环为后移插入
        • 一层循环内,先判断a[i]与前一个是否无序,若无序那就排序,temp保存关键字,low=0,high=i-1;进入二层循环,当low<=high的时候,mid=(low+high)/2,折半查找根据不同情况更改low或high的值,跳出循环说明找到位置,用j进行后移插入
    • 希尔排序:使用直接插入算法实现分组排序,组越分越小,最后完全有序
  • 交换排序
    • 冒泡排序:从后往前,挨个比较交换,每次排出一个最小的,前面为全局有序区
      • 接口:无序数组A,数组长度n
      • 临时变量
        • i表示i次遍历排出i个有序数列,j用来从后往前比较交换
      • 运算过程
        • 两层循环,一层用i表示i次排序,j用来从后向前直到i那里进行交换
    • 快速排序:每次将一个基准排到正确的位置,以此为基准划分左右两块区域,递归调用快速排序算法
      • 接口:无序数组A,low,high待排序区间
      • 临时变量
        • int pivot基准
      • 运算过程
        • 一层循环里面嵌套递归
        • 当low<high时循环,排序第一个关键字并获取基准,根据基准递归调用快速排序左右子序列
        • 划分函数
          • 接口:无序数组A,low,high
          • 返回值:基准物理位置
          • 临时变量
            • pivot基准保存待排序的基准关键字
          • 运算过程
            • 两层循环,一层左右遍历序列,二层用来左右横跳
            • 先保存第一个关键字为基准,当low<=high开始循环,先从后往前找到一个小于基准的往前放,然后从前往后找一个大于基准的往后放,最后跳出循环剩下的位置放基准,返回基准位置
  • 选择排序:每次选择一个最大或最小的放进全局有序区,
    • 简单选择排序:每次从后面找到一个最小的,往前放
      • 接口:无序数字A,长度n
      • 临时变量:i代表有序区,j遍历无序区,min保存最小下标
      • 运算过程
        • 两层循环,一层遍历n遍,二层遍历无序区找最小
        • 当i<n循环,min取i,用j从后向前循环,若遇到比min还小的,min取而代之,循环完,发现min值改变,交换a[i],a[min]
    • 堆排序:将数组看成满二叉树的顺序存储结构,先从最后一个分支节点逐个筛选上浮,然后或得一个大根堆,将最大值根与最后一个叶子节点交换,然后再次对根节点进行筛选使之成为大根堆
      • 接口:无序数组A,长度n
      • 临时变量:
        • i用来循环建立初始根堆,以及逐次的根节点交换后排序
      • 运算过程:
        • 先建立大根堆,i初始为n/2表示最后一个分支节点,当i>=0时i–从后向前逐个进行筛选操作sift(a,i,n),形成大根堆
        • 然后交换根节点和最后一个叶子节点,对根节点进行筛选sift(a,1,i-1),循环i=n,i>1,i–从后向前,每次算拍好一个最大值,
        • 筛选函数sift:先保存待筛选关键字为temp,找出他的最大的一个孩子与父母对比,若比父母大则和父母交换,若破坏了自身大堆性则循环比较孩子和父母的关系,正常则跳出,这时找到temp的位置放入
          • 接口:无序数组a,low,high排序区间
          • 临时变量:
            • i用来表示父母和最后的位置,j表示孩子,temp保存待筛选关键字
          • 运算过程:
            • i=low,j=2*i,temp=a[i]
            • 一层循环调整大根堆并找到带筛选关键字的位置,先比较孩子大小,若孩子比父母大,a[i]=a[j]进行替换,若正常跳出循环,这个循环一直进行到正常,保证替换后的都是大根堆,最后i表示筛选后的位置,a[i]=temp;
  • 归并排序:不断二路基本归并,归并的长度2的倍数递增直到为序列长度,需要一个额外的数组
    • 二路归并
      • 接口:无序数组A,low,mid,high表示归并的区间
      • 临时变量:r1接受比较后的序列,i,j遍历二路,k遍历r1
      • 运算过程:
        • 一层循环分别比较二路,哪边小放入r1
        • 将二路剩下录入r1
        • r1反过来给r,销毁r1
  • 基数排序:根据基数排序,排位数次,重要性从小到大的排序
  • 算法对比
    • 插入排序
      • 简单插入
      • 折半插入
      • 希尔排序
    • 交换排序
      • 冒泡排序
      • 快速排序
    • 选择排序
      • 简单选择排序
      • 堆排序
    • 归并排序
    • 基数排序
    • 时间复杂度
      • 初级算法都是n^2
      • 改进算法都是nlogn
      • 希尔排序和基数排序特殊
      • 插入和冒泡排序有最好情况,快速排序有最差情况为n^2
    • 空间复杂度
      • 快速排序:log_2 n
      • 二路归并: n
      • 基数:r
    • 稳定性
      • 直,冒,归,基稳定
    • 全局有序
      • 交换排序和选择排序

猜你喜欢

转载自blog.csdn.net/weixin_43231912/article/details/122284358