02,数据结构简介

数据结构

数据结构是为实现对计算机数据有效使用的各种数据组织形式,服务于各类计算机操作。
不同的数据结构具有各自对应的适用场景,旨在降低各种算法计算的时间与空间复杂度,达到最佳的任务执行效率。

常见数据结构

线性数据结构

数组(Array)

数组是存放在连续内存空间上相同类型数据的集合,其长度不可变。
因为数组的在内存空间的地址是连续的,所以在删除或者增添元素的时候,就难免要移动其他元素的地址。
数组的元素是不能删的,只能覆盖。

链表(Linked List)

链表是一种通过指针串联在一起的线性结构,每一个节点由两部分组成,一个是数据域一个是指针域(存放指向下一个节点的指针),最后一个节点的指针域指向null(空指针的意思)。链接的入口节点称为链表的头结点也就是head。

链表种类

单链表:上述,单链表中的节点只能指向节点的下一个节点
双链表:每个节点有两个指针域,一个指向下一个节点,一个指向上一个节点。可向前查询和向后查询

循环链表:链表首尾相连

链表的存储方式

链表在内存中不是连续分布的,而是通过指针域的指针链接在内存中各个节点,所以是散乱分布在内存中的某地址上,分配机制取决于操作系统的内存管理。

栈(Stack)

栈是一种具有先入后出特点的抽象数据结构,可使用数组或链表实现。
常用操作:入栈push(),出栈pop()

队列(Queue)

队列是一种具有先入先出特点的抽象数据结构,可使用链表实现。
常用操作:入队push(),出队pop()

非线性数据结构

树(Tree)

树是一种非线性数据结构,根据子节点数量可分为 「二叉树」 和 「多叉树」,最顶层的节点称为「根节点 root」。以二叉树为例,每个节点包含三个成员变量:「值 val」、「左子节点 left」、「右子节点 right」 。

二叉树的种类

满二叉树:如果一棵二叉树只有度为0的结点和度为2的结点,并且度为0的结点在同一层上,则这棵二叉树为满二叉树。深度为k,有2^k-1个节点。

完全二叉树:在完全二叉树中,除了最底层节点可能没填满外,其余每层节点数都达到最大值,并且最下面一层的节点都集中在该层最左边的若干位置。若最底层为第 h 层,则该层包含 1~ 2^(h-1)  个节点。

二叉搜索树

二叉搜索树是有数值的了,二叉搜索树是一个有序树
  • 若它的左子树不空,则左子树上所有结点的值均小于它的根结点的值;
  • 若它的右子树不空,则右子树上所有结点的值均大于它的根结点的值;
  • 它的左、右子树也分别为二叉排序树

平衡二叉搜索树/AVL树

是一棵空树或它的左右两个子树的高度差的绝对值不超过1,并且左右两个子树都是一棵平衡二叉树。

二叉树的存储方式

可以链式存储,也可以顺序存储。链式存储方式就用指针, 顺序存储的方式就是用数组。

链式存储:通过指针把分布在散落在各个地址的节点串联一起。


顺序存储:如果父节点的数组下标是 i,那么它的左孩子就是 i * 2 + 1,右孩子就是 i * 2 + 2。

二叉树的遍历方式

  • 深度优先遍历:先往深走,遇到叶子节点再往回走。
  1. 前序遍历(递归法,迭代法):中左右
  2. 中序遍历(递归法,迭代法):左中右
  3. 后序遍历(递归法,迭代法):左右中
  • 广度优先遍历:一层一层的去遍历。
  1. 层次遍历(迭代法)

堆(Heap)

堆是一种基于「完全二叉树」的数据结构,可使用数组实现。
以堆为原理的排序算法称为「堆排序」,基于堆实现的数据结构为「优先队列」。通过使用「优先队列」的「压入push()」和「弹出pop()」操作,即可完成堆排序。
堆分为「大顶堆」和「小顶堆」,大(小)顶堆:任意节点的值不大于(小于)其父节点的值。
from heapq import heappush, heappop

# 初始化小顶堆
heap = []

# 元素入堆
heappush(heap, 1)
heappush(heap, 4)
heappush(heap, 2)
heappush(heap, 6)
heappush(heap, 8)

# 元素出堆(从小到大)
heappop(heap) # -> 1
heappop(heap) # -> 2
heappop(heap) # -> 4
heappop(heap) # -> 6
heappop(heap) # -> 8

散列表/哈希表(Hashing)

散列表是一种非线性数据结构,通过利用 Hash 函数将指定的「键key」映射至对应的「值value」,以实现高效的元素查找。

哈希碰撞的两种解决方法

将不同的键映射到了相同索引下标位置,这种想象称为哈希碰撞(collisions)
1,拉链法??
要选择适当的哈希表的大小,这样既不会因为数组空值而浪费大量内存,也不会因为链表太长而在查找上浪费太多时间。
2,线性探测法:要保证tableSize大于dataSize,依靠哈希表中的空位来解决碰撞问题。

图(Graph)

图是一种非线性数据结构,由「节点(顶点)vertex」和「边edge」组成,每条边连接一对顶点。根据边的方向有无,图可分为「有向图」和「无向图」。

图的表示方法

1,邻接矩阵:使用数组vertices 存储顶点,邻接矩阵edges 存储边;edges[i][j] 代表节点i+1 和 节点j+1 之间是否有边。
2,邻接表:使用数组vertices 存储顶点,邻接表edges 存储边,edges 为一个二维容器,第一维i代表顶点索引,第二维 edges[i] 存储此顶点对应的边集和。

**两种方式比较

邻接矩阵的大小只与节点数量有关,即N^2 ,其中N为节点数量。因此,当边数量明显少于节点数量时,使用邻接矩阵存储图会造成较大的内存浪费。

因此,邻接表 适合存储稀疏图(顶点较多、边较少); 邻接矩阵 适合存储稠密图(顶点较少、边较多)。









全部评论

相关推荐

11-24 00:11
已编辑
广东工业大学 算法工程师
避雷深圳  yidao,试用期 6 个月。好嘛,试用期还没结束,就直接告诉你尽快找下一家吧,我谢谢您嘞
牛客75408465号:笑死,直属领导和 hr 口径都没统一,各自说了一些离谱的被裁理由,你们能不能认真一点呀,哈哈哈哈哈😅😅😅
点赞 评论 收藏
分享
冷艳的小师弟在看机会:jd测评乱点直接被挂了,哭死~
点赞 评论 收藏
分享
美丽的查理斯不讲武德:包kpi的啊,感觉虾皮一点hc都没有
点赞 评论 收藏
分享
点赞 收藏 评论
分享
牛客网
牛客企业服务