CSDN 的小伙伴们,大家好,我是沉默的王二。

假期结束了,需要快速切换到工作的状态投入到新的一天当中。放假的时候痛快地玩耍,上班的时候积极的工作,这应该是我们大多数“现代人”该有的生活状态。

今天我们来学一下数据结构方面的知识,对扎实 Java 的基本功非常有用,学会了就会有一种自带大佬的感觉,嘿嘿。数据结构,也就是 Data Structure,是一种存储数据的结构体,数据与数据之间存在着一定的关系,这样的关系有数据的逻辑关系、数据的存储关系和数据的运算关系。

在 Java 中,数据结构一般可以分为两大类:线性数据结构和非线性数据结构。哈哈,这个非字很有灵魂吧?

先来说线性数据结构吧。

1)数组

一眼看上去就知道的,像 String []int [] 这种;还有需要看两眼才能看透的(看源码了),像 ArrayList,内部对数组进行了封装。

数组这种数据结构最大的好处,就是可以根据下标(或者叫索引)进行操作,插入的时候可以根据下标直接插入到具体的位置,但与此同时,后面的元素就需要全部向后移动,需要移动的数据越多,就越累。

假设现在已经有了一个 ArrayList 了,准备在第 4 个位置(下标为 3)上添加一个元素 55。

此时 ArrayList 中第 5 个位置以后的元素将会向后移动。

准备把 23 从 ArrayList 中移除。

此时下标为 7、8、9 的元素往前挪。

简单总结一下 ArrayList 的时间复杂度,方便大家在学习的时候作为参考。

1、通过下标(也就是 get(int index))访问一个元素的时间复杂度为 O(1),因为是直达的,无论数据增大多少倍,耗时都不变。

2、添加一个元素(也就是 add())的时间复杂度为 O(1),因为直接添加到末尾。

3、删除一个元素的时间复杂度为 O(n),因为要遍历列表,数据量增大几倍,耗时也增大几倍。

4、查找一个未排序的列表时间复杂度为 O(n),因为要遍历列表;查找排序过的列表时间复杂度为 O(log n),因为可以使用二分查找法,当数据增大 n 倍时,耗时增大 logn 倍(这里的 log 是以 2 为底的,每找一次排除一半的可能)。

2)链表

链表在物理存储空间是不连续的,但每个节点要么知道它的下一个节点是谁,要么知道它的上一个节点是谁,仿佛就像我们之间隔着千山万水,却心有灵犀一点链。像 LinkedList 就是最典型的链表结构,通过引用相互链接。

LinkedList 中的每一个元素都可以称之为节点(Node),每一个节点都包含三个项目:其一是元素本身,其二是指向下一个元素的引用地址,其三是指向上一个元素的引用地址。

LinkedList 看起来就像下面这个样子:

  • 第一个节点由于没有前一个节点,所以 prev 为 null;
  • 最后一个节点由于没有后一个节点,所以 next 为 null;
  • 这是一个双向链表,每一个节点都由三部分组成,前后节点和值。

相比 ArrayList,LinkedList 有以下优势:

1、LinkedList 允许内存进行动态分配,这就意味着内存分配是由编译器在运行时完成的,我们无需在 LinkedList 声明的时候指定大小。

2、LinkedList 不需要在连续的位置上存储元素,因为节点可以通过引用指定下一个节点或者前一个节点。也就是说,LinkedList 在插入和删除元素的时候代价很低,因为不需要移动其他元素,只需要更新前一个节点和后一个节点的引用地址即可。

3)栈

栈是一种非常有用的数据结构,它就像一摞盘子,第一个放在最下面,第二个放在第一个上面,第三个放在第二个上面,最后一个放在最上面。栈遵循后进先出的原则,也就是“Last In First Out”(简称 LIFO)——最后的一个进的,最先出去。

对于栈这样一个数据结构来说,它有两个常见的动作:

  • push,中文释义有很多种,我个人更喜欢叫它“压入”,非常形象。当我们要把一个数据放入栈的顶部,这个动作就叫做 push

  • pop,同样的,我个人更喜欢叫它“弹出”,带有很强烈的动画效果,有没有?当我们要从栈中移除一个数据时,这个动作就叫做 pop

4)队列

队列,只允许在队尾添加数据,队首移除数据。队列在 Java 中的出现频率非常高,有各种不同的类来满足不同的场景需求。像优先级队列 PriorityQueue、延时队列 DelayQueue 等等。队列遵循的是 First In First Out,缩写为 FIFO,也就是先进先出,第一个进入队列的第一个先出来。

再来说非线性数据结构。

1) 树

树是一种典型的非线性结构,它是由 n(n>0)个有限节点组成的一个具有层次关系的集合。之所以叫“树”,是因为这种数据结构看起来就像是一个倒挂的树,只不过根在上,叶在下。树形数据结构有以下这些特点:

  • 每个节点都只有有限个子节点或无子节点;
  • 没有父节点的节点称为根节点;
  • 每一个非根节点有且只有一个父节点;
  • 除了根节点外,每个子节点可以分为多个不相交的子树。

下图展示了树的一些术语:

根节点是第 0 层,它的子节点是第 1 层,子节点的子节点为第 2 层,以此类推。

  • 深度:对于任意节点 n,n 的深度为从根到 n 的唯一路径长,根的深度为 0。
  • 高度:对于任意节点 n,n 的高度为从 n 到一片树叶的最长路径长,所有树叶的高度为 0。

树又可以细分为下面几种:

1、普通树:对子节点没有任何约束。

2、二叉树:每个节点最多含有两个子节点的树。 二叉树按照不同的表现形式又可以分为多种。

2.1、普通二叉树:每个子节点的父节点不一定有两个子节点的二叉树。

2.2、完全二叉树:对于一颗二叉树,假设其深度为d(d>1)。除了第 d 层外,其它各层的节点数目均已达最大值,且第 d 层所有节点从左向右连续地紧密排列。

2.3、满二叉树:一颗每一层的节点数都达到了最大值的二叉树。有两种表现形式,第一种,像下图这样(每一层都是满的),满足每一层的节点数都达到了最大值 2。

3、二叉查找树:英文名叫 Binary Search Tree,即 BST,需要满足以下条件:

  • 任意节点的左子树不空,左子树上所有节点的值均小于它的根节点的值;
  • 任意节点的右子树不空,右子树上所有节点的值均大于它的根节点的值;
  • 任意节点的左、右子树也分别为二叉查找树。

3.1、平衡二叉树:当且仅当任何节点的两棵子树的高度差不大于 1 的二叉树。由前苏联的数学家 Adelse-Velskil 和 Landis 在 1962 年提出的高度平衡的二叉树,根据科学家的英文名也称为 AVL 树。

平衡二叉树本质上也是一颗二叉查找树,不过为了限制左右子树的高度差,避免出现倾斜树等偏向于线性结构演化的情况,所以对二叉搜索树中每个节点的左右子树作了限制,左右子树的高度差称之为平衡因子,树中每个节点的平衡因子绝对值不大于 1。

平衡二叉树的难点在于,当删除或者增加节点的情况下,如何通过左旋或者右旋的方式来保持左右平衡。

红黑树是一种常见的平衡二叉树,节点是红色或者黑色,通过颜色的约束来维持着二叉树的平衡:

  • 每个节点都只能是红色或者黑色
  • 根节点是黑色
  • 每个叶节点(NIL 节点,空节点)是黑色的。
  • 如果一个节点是红色的,则它两个子节点都是黑色的。也就是说在一条路径上不能出现相邻的两个红色节点。
  • 从任一节点到其每个叶子的所有路径都包含相同数目的黑色节点。

4、B 树:一种对读写操作进行优化的自平衡的二叉查找树,能够保持数据有序,拥有多于两个的子树。

5、B+ 树:B 树的变体。

HashMap 里面的 TreeNode 就用到了红黑树,而 B 树、B+ 树在数据库的索引原理里面有典型的应用。

2)哈希表

哈希表(Hash Table),也叫散列表,是一种可以通过关键码值(key-value)直接访问的数据结构,它最大的特点就是可以快速实现查找、插入和删除。其中用到的算法叫做哈希,就是把任意长度的输入,变换成固定长度的输出,该输出就是哈希值。像 MD5、SHA1 都用的是哈希算法。

每一个 Java 对象都会有一个哈希值,默认情况就是通过调用本地方法执行哈希算法,计算出对象的内存地址 + 对象的值的关键码值。

数组的最大特点就是查找容易,插入和删除困难;而链表正好相反,查找困难,而插入和删除容易。哈希表很完美地结合了两者的优点, Java 的 HashMap 在此基础上还加入了树的优点。

哈希表具有较快(常量级)的查询速度,以及相对较快的增删速度,所以很适合在海量数据的环境中使用。

对于任意两个不同的数据块,其哈希值相同的可能性极小,也就是说,对于一个给定的数据块,找到和它哈希值相同的数据块极为困难。再者,对于一个数据块,哪怕只改动它的一个比特位,其哈希值的改动也会非常的大——这正是 Hash 存在的价值!

尽管可能性极小,但仍然会发生,如果哈希冲突了,Java 的 HashMap 会在数组的同一个位置上增加链表,如果链表的长度大于 8,将会转化成红黑树进行处理——这就是所谓的拉链法(数组+链表)。

3)图

图是一种复杂的非线性结构,由顶点的有穷非空集合和顶点之间边的集合组成,通常表示为:G(V,E),其中,G 表示一个图,V 是图 G 中顶点的集合,E 是图 G 中边的集合。

上图共有 V0,V1,V2,V3 这 4 个顶点,4 个顶点之间共有 5 条边。

在线性结构中,数据元素之间满足唯一的线性关系,每个数据元素(除第一个和最后一个外)均有唯一的“前驱”和“后继”;

在树形结构中,数据元素之间有着明显的层次关系,并且每个数据元素只与上一层中的一个元素(父节点)及下一层的多个元素(子节点)相关;

而在图形结构中,节点之间的关系是任意的,图中任意两个数据元素之间都有可能相关。

最后,希望大家都能把 Java 数据结构学好,从一键三连做起吧

推荐阅读:

V4.0 《JavaGuide 面试突击版》来啦!GitHub 上标星 98.1k,帮你成功上岸!

学弟学妹们,学会霍夫曼编码后,再也不用担心网络带宽了!

16 张图带你搞懂 Java 数据结构,从此想不飘都难!相关推荐

  1. 哪吒社区技能树16 张图带你搞懂 Java 数据结构,从此想不飘都难

    目录 一.数组 二.链表 三.栈 四.队列 五. 树 1.普通树:对子节点没有任何约束.​ 2.二叉树:每个节点最多含有两个子节点的树. 二叉树按照不同的表现形式又可以分为多种. 3.二叉查找树:英文 ...

  2. 「八大排序算法」16张图带你搞懂基数排序

    前言 在排序算法中,大家可能对桶排序.计数排序.基数排序不太了解,不太清楚其算法的思想和流程,也可能看过会过但是很快就忘记了,但是不要紧,幸运的是你看到了本篇文章.本文将通俗易懂的给你讲解基数排序. ...

  3. 转载 硬核图解!30张图带你搞懂!路由器,集线器,交换机,网桥,光猫有啥区别?

    硬核图解!30张图带你搞懂!路由器,集线器,交换机,网桥,光猫有啥区别?... 煎鱼(EDDYCJY) 于 2022-01-17 08:51:00 发布 1219 已收藏 22 文章标签: 交换机 网 ...

  4. java队列_如何彻底搞懂 Java 数据结构?CSDN 博文精选

    作者 | 张振华.Jack 责编 | 郭芮 出品 | CSDN 博客 本文和大家一起来重温<Java数据结构>经典之作. Java数据结构 要理解Java数据结构,必须能清楚何为数据结构? ...

  5. 如何彻底搞懂 Java 数据结构?|CSDN 博文精选

    作者 | 张振华.Jack 责编 | 郭芮 出品 | CSDN 博客 本文和大家一起来重温<Java数据结构>经典之作. Java数据结构 要理解Java数据结构,必须能清楚何为数据结构? ...

  6. java 固定长度队列_如何彻底搞懂 Java 数据结构?|CSDN 博文精选

    作者 | 张振华.Jack 责编 | 郭芮 出品 | CSDN 博客 本文和大家一起来重温<Java数据结构>经典之作. Java数据结构 要理解Java数据结构,必须能清楚何为数据结构? ...

  7. 一张图带你搞懂Javascript原型链关系

    在某天,我听了一个老师的公开课,一张图搞懂了原型链. 老师花两天时间理解.整理的,他讲了两个小时我们当时就听懂了. 今天我把他整理出来,分享给大家.也让我自己巩固加深一下. 就是这张图: 为了更好的图 ...

  8. 推荐一篇微服务硬核文章 6 张图带你搞懂微服务

    我是非典型理科男号主.点击上方蓝字关注. 关注后你可以收获最硬核的知识分享, 最有趣的互联网故事 推荐老王的一篇关于微服务的文章. 通过文章你可以了解到 单体架构到微服务架构的变化,ServiceMe ...

  9. 40 张图带你搞懂 TCP 和 UDP

    前言 拿下计网协议后,我就是公园里最靓的仔 TCP/IP 基础知识总结 计算机网络基础知识总结 那么下面就开始我们本篇文章,文章组织脉络如下 运输层位于应用层和网络层之间,是 OSI 分层体系中的第四 ...

最新文章

  1. Atitit.eclipse 4.3 4.4  4.5 4.6新特性
  2. asp.net + winform + log4net 使用示例|using log4net with asp.net/winform
  3. 数据库跟尾过多的错误,能够的原因阐发及处置惩罚设备
  4. JDBC 4.2 Specifications 中文翻译 -- 第九章 连接
  5. python中的with
  6. 上传jar包到nexus私服
  7. php验证手机验证码过期,验证过期时间
  8. 查询mysql所有表的大小
  9. linux 进程优先级 调度 nice pri
  10. OC高效率52之提供“全能初始化”方法
  11. 微型计算机天逸510s光驱,天逸510s Mini兼macOS BigSur安装教程
  12. SRAM and DRAM
  13. 【Unity Shader】(2)半兰伯特模型 构建光照
  14. 33220a 编程C语言,基于AT89C51单片机的数字式波形发生器(非常完整).doc
  15. elasticsearch 学习笔记3
  16. 证明三角形全等的方法
  17. Java读取word文档里的复杂型表格(任免表)
  18. ArcGIS中根据DEM和地形起伏度进行地貌分类划分
  19. 音乐机器人特奥_网红机器人特奥挑战人类钢琴家音乐会
  20. 中国手机地图用户超7千万 LBS开启掌上世界

热门文章

  1. matlab比例环节代码,典型环节的MATLAB仿真
  2. c语言记账系统源程序,C语言实现Linux服务端的记账本程序
  3. socket通信read丢失数据可能原因
  4. html 设置min height,CSS中min-height使用技巧
  5. 31 《象与骑象人:幸福的假设》 -豆瓣评分8.4
  6. web前端期末大作业 html+css+javascript网页设计实例 宠物狗网站制作
  7. Spring Security OAuth2.0认证授权五:用户信息扩展到jwt
  8. Windows 局域网间如何共享文件
  9. ftp服务器必须运行ftp服务器软件对吗,ftp是什么?FTP服务器搭建及选择
  10. 设计一个圆形文字LOGO