快速入门数据结构
百科:
推荐链接:
前言
为什么要学习算法和数据结构?
- 解决特定问题。
- 深度优化程序性能的基础。
- 学习一种思想:如何把现实问题转化为计算机语言表示。
业务开发要掌握到程度?
- 了解常见数据结构和算法,沟通没有障碍。
- 活学活用:遇到问题时知道要用什么数据结构和算法去优化。
数据结构基础
什么是数据结构
数据结构是数据的组织、管理和存储格式,其使用目的是为了高效的访问和修改数据。
数据结构是算法的基石。如果把算法比喻成美丽灵动的舞者,那么数据结构就是舞者脚下广阔而坚实的舞台。
物理结构和逻辑结构的区别
物理结构就像人的血肉和骨骼,看得见,摸得着,实实在在,如数组、链表。
逻辑结构就像人的思想和精神,它们看不见、摸不着,如队列、堆栈、树、图。
线性存储结构和非线性存储结构的区别
线性:元素之间的关系是一对一的,如堆栈、队列。
非线性:每个元素可能连接0或多个元素,如树、图。
常见数据结构
数组
什么是数组
数据是有限个相同类型的变量所组成的有序集合。数组中的每一个变量被称为元素。
数组的基本操作
读取O(1)、更新O(1)、插入O(n)、删除O(n)、扩容O(n)。
链表
什么是链表
链表是一种在物理上非连续、非顺序的数据结构,由若干个节点组成。
单向链表的每一个节点又包含两部分,一部分是存放数据的变量data,另一部分是指向下一个节点的指针next。
链表的基本操作
读取O(n)、更新O(1)、插入O(1)、删除O(1)。
链表 VS 数组
数组:适合多读、插入删除少的场景。
链表:适用于插入删除多、读少的场景。
栈
什么是栈
栈是一种线性逻辑数据结构,栈的元素只能后进先出。最早进入的元素存放的位置叫做栈底,最后进入的元素存放的位置叫栈顶。
一个比喻,栈是一个一端封闭一端的开放的中空管子,队列是两端开放的中空管子。
如何实现栈
数组实现:
链表实现:
栈的基本操作
入栈O(1)、出栈O(1)。
栈的应用
- 回溯历史,比如方法调用栈。
- 页面面包屑导航。
队列
什么是队列
一种线性逻辑数据结构,队列的元素只能后进后出。队列的出口端叫做队头,队列的入口端叫做队尾。
如何实现队列
数组实现:
链表实现:
队列的基本操作
入队 O(1)、出队 O(1)。
队列的应用
- 消息队列
- 多线程的等待队列
- 网络爬虫的待爬URL队列
哈希表
什么是哈希表
一种逻辑数据结构,提供了键(key)和值(value)的映射关系。
哈希表的基本操作
写入:O(1)、读取:O(1)、扩容O(n)。
什么是哈希函数
哈希表本质上是一个数组,只是数组只能根据下标,像a[0] a[1] a[2] a[3] 这样来访问,而哈希表的key则是以字符串类型为主的。
通过哈希函数,我们可以把字符串或其他类型的key,转化成数组的下标index。
如给出一个长度为8的数组,则:
当 key=001121 时,
1 | index = HashCode ("001121") % Array.length = 7 |
当 key=this 时,
1 | index = HashCode ("this") % Array.length = 6 |
什么是哈希冲突
不同的key通过哈希函数获得的下标有可能是相同的,例如002936这个key对应的数组下标是2,002947对应的数组下标也是2,这种情况就是哈希冲突。
如何解决哈希冲突
开放寻址法:例子Threadlocal。
链表法:例子Hashmap。
树
什么是树
树(tree)是n(n≥0)个节点的有限集。
当n=0时,称为空树。在任意一个非空树中,有如下特点:
有且仅有一个特定的称为根的节点。
当n>1时,其余节点可分为m(m>0)个互不相交的有限集,每一个集合本身又是一个树,并称为根的子树。