我对八种常见数据结构的理解(3)

同样的看名字你也可以知道,这是代码执行的总次数很多,每次都要运行 n 次, 所以表示为 O(n)。这是我们写代码最不想要的。当然这也是不现实的。

3.平均时间复杂度: 就是把最好情况时间复杂度和最坏情况时间复杂度求取一平均值, 这是我们写代码最有意义的,因为这是期望的运行时间,所以在写代码时应当考虑这一点。

常见复杂度:

还有一个重要的概念:算法空间复杂度

所谓算法的空间复杂度就是通过计算机算法所需求的存在空间实现。 计算公式可以表示为:S(n) = O( f(n) ),其中,n 为问题的规模, f(n) 为语句关于 n 所占存储空间的函数。

一般情况下,一个程序在机器上运行时,除了考虑到程序的本身运行指令, 常数,变量和输入数据外,还需要考虑存储对数据操作的存储单元.我们在写代码 时完全可以用空间换取时间,两者不存在绝对的好与坏,这么用好二者关系取决于 你用在什么地方。所以,实际情况还是要根据工程代码做最完美的选择。

时间复杂度大 O 表示方法的由来。 大 O 推导的表示方法和常用的大 O 表示法时间复杂度。 时间复杂度的三种情况:最好情况、最坏情况和平均情况。 算法空间复杂度,适当情况可以用空间换取时间。

但不论怎么样,我们学习 Big O 的根本目的就是:用 Big O 方法帮帮助我们从各种编码思路中,找到最合适的那一种方案

数据结构是啥?

======================================================================

还有朋友可能不太理解什么是数据结构,就像喝水,你总是喝到最上面的一层,我称之为“水的栈”这便是一种结构

顾名思义数据结构,便是数据的结构,数据结构并不是什么很高深的东西

起初数据结构并没有一门专门的学科,并不是没有就代表不存在

我问大家一个问题,先有数据结构还是先有的编程?

瑞典计算机科学家 Niklaus Wirth 在 1976 年写了一本书,叫作《Algorithms + Data Structures = Programs》,数据结构的学科便从此发展的不可收拾

要知道早在 1949 年汇编就诞生了

其实深究这个问题是没有任何意义的,如 Niklaus Wirth 的书名:《Algorithms + Data Structures = Programs》

学习数据结构的目的就是为了让我们理解数据在计算机里的存储结构

树?图?栈?

别被这些名词给吓到了,例如"树",你就可以理解数据在计算机中是像树一样的存储,不妨打开你的电脑,随便看一看自己的文件目录,是不是就像一颗树一样

数组

=================================================================

关于数组的知识,我想是我们每个初学者的必学必备

但我想没多少人能真正理解到——数组其实就是一种数据结构

一维数组就是一行数据,n 个数据,二维数组就是 n 行,m 列,n*m 个数据,那三维数组呢?除此之外还有五维、六维。。。。直到内存爆炸,这该怎么描述?所以死记硬背是行不通的,只有了解其底层含义才能通向罗马。

如图:不同维度的数组长这样

很简单是不是?

高纬度嵌套低纬度,同时高纬度等于下一级维度的 2 倍

接下来就是数组优点:

1、按照索引查询元素速度快

例如 j[1]

2、按照索引遍历数组方便

例如 j[i]

缺点:

1、数组的大小固定后就无法扩容了

2、数组只能存储一种类型的数据

3、添加,删除的操作慢,因为要移动其他的元素。

适用场景:

频繁查询,对存储空间要求不大,很少增加和删除的情况。

扩展:

我们也可以

创造一个简单

存储字符串的动态数组

像 List 一样存储数据

运行结果:

感受到数据结构的魅力了吗?

你所使用的容器,也都是被前辈们这样基于底层创造出来的,当然了,他们更强大

================================================================

栈的结构如图:

之前我们提到了:

数据结构就像喝水,你总是喝到最上面的一层,我称之为“水的栈”这便是一种结构

所以你可以把栈的结构理解为一杯水

栈顶为杯口,栈底理解为杯底

而水只能从杯口出入,栈内的数据也只能从栈顶提取/输入

不借助任何工具,喝水时你总是喝到离杯口最近的水,往水杯里加水你也不可能从水杯中间加水

栈也是如此,你只能从栈顶按顺序提取数据,所以插入数据你需要将索引位置以上的数据都提取出来,再插入,而后将提取出的数据再依次存入

基本算法

1.进栈(PUSH)算法

① 若 TOP≥n 时,则给出溢出信息,作出错处理(进栈前首先检查栈是否已满,满则溢出;不满则作 ②);

② 置 TOP=TOP+1(栈指针加 1,指向进栈地址);

③S(TOP)=X,结束(X 为新进栈的元素);

2.退栈(POP)算法

① 若 TOP≤0,则给出下溢信息,作出错处理(退栈前先检查是否已为空栈, 空则下溢;不空则作 ②);

②X=S(TOP),(退栈后的元素赋给 X):

③TOP=TOP-1,结束(栈指针减 1,指向栈顶)。

栈常应用于实现递归功能方面的场景,例如斐波那契数列。

好理解吧!

栈就是一种特殊的线性表,仅能在线性表的一端操作,栈顶允许操作,栈底不允许操作

栈的特点是:先进后出,或者说是后进先出,从栈顶放入元素的操作叫入栈,取出元素叫出栈。

队列

=================================================================

队列和栈一样,也是一种线性表

队列的结构长这样:

但也有队列也有和栈的不同之处:

可以简单理解为队列为没有杯底的杯子,一端负责进水,一端负责出水

也就是:先进先出,从一端放入元素的操作称为入队,取出元素为出队

使用场景:因为队列先进先出的特点,在多线程阻塞队列管理中非常适用

链表

=================================================================

把一堆扑克牌丢地上,反面朝上,你能找到,哪张是梅花 A 吗?

如果正面朝上呢?

上面的例子很清晰的描述了链表的特点

链表是一种物理存储结构上非连续,非顺序的存储结构

数据元素的逻辑顺序是通过链表中的指针链接次序实现的

指针指向的就是数据的地址

反面朝上的扑克牌代表内存里的数据,如果正面朝上就代表我们赋予其地址,根据地址来操纵数据

此时你还能找到梅花 A 吗?

答:能!

*p = ♣A

所以链表的结构长这样:

无头单向非循环列表:结构简单,一般不会单独用来存放数据。实际中更多是作为其他数据结构的子结构,比如说哈希桶等等

带头双向循环链表:结构最复杂,一般单独存储数据。实际中经常使用的链表数据结构,都是带头双向循环链表。这个结构虽然复杂,但是使用代码实现后会发现这个结构会带来很多优势,实现反而简单了

单链表和双链表的区别:

单链表的每一个节点中只有指向下一个结点的指针,不能进行回溯,适用于节点的增加和删除。

双链表的每一个节点给中既有指向下一个结点的指针,也有指向上一个结点的指针,可以快速的找到当前节点的前一个节点,适用于需要双向查找节点值的情况

为啥可以这么多样式?

因为指针就是这么方便!

话说。。有没有感觉和数组有点像了?

链表和数组的区别:

数组静态分配内存,链表动态分配内存

数组在内存中是连续的,链表是不连续的

数组利用下标定位,查找的时间复杂度是 O(1),链表通过遍历定位元素,查找的时间复杂度是 O(N)

数组插入和删除需要移动其他元素,时间复杂度是 O(N),链表的插入或删除不需要移动其他元素,时间复杂度是 O(1)

稍微分析下是不是就会发现,各有各的优缺点?

所以存在即合理,每一种数据结构都有它的特点,并不是哪种好,哪种坏

================================================================

直接放图:

还有比这更容易理解的了吗?

如果不理解就把"A"节点当作爷爷,“D”节点当作父亲,"H"节点当作小孩

树是一种数据结构

它是由 n(n>=1)个有限节点组成一个具有层次关系的集合。把它叫做 “树” 是因为它看起来像一棵倒挂的树,也就是说它是根朝上,而叶朝下的。它具有以下的特点:

每个节点有零个或多个子节点;

没有父节点的节点称为根节点;

每一个非根节点有且只有一个父节点;

除了根节点外,每个子节点可以分为多个不相交的子树;

在日常的应用中,我们讨论和用的更多的是树的其中一种结构,就是

二叉树

为啥?

因为二叉树十分强大

二叉树是树的特殊一种,具有如下特点:

1、每个结点最多有两颗子树,结点的度最大为 2。

2、左子树和右子树是有顺序的,次序不能颠倒。

3、即使某结点只有一个子树,也要区分左右子树。

二叉树是一种比较有用的折中方案,它添加,删除元素都很快,并且在查找方面也有很多的算法优化,所以,二叉树既有链表的好处,也有数组的好处,是两者的优化方案,在处理大批量的动态数据方面非常有用。

扩展:

二叉树有很多扩展的数据结构,包括:

平衡二叉树、红黑树、B+树等

这些数据结构二叉树的基础上衍生了很多的功能

在实际应用中广泛用到,例如:

mysql的数据库索引结构用的就是B+树;还有HashMap的底层源码中用到了红黑树

这些二叉树的功能强大,但算法上比较复杂, 我还需要花时间去深入

哈希表

==================================================================

Hash table = 散列表

这两是一个东西

先看百度百科怎么说:

散列表(Hash table,也叫哈希表),是根据键(Key)而直接访问在内存存储位置的数据结构。也就是说,它通过计算一个关于键值的函数,将所需查询的数据映射到表中一个位置来访问记录,这加快了查找速度。这个映射函数称做散列函数,存放记录的数组称做散列表

哈希表其实本质是数组

这要说到 Hash table 的两种实现方法:

1、数组+链表

2、数组+二叉树

区别在于:

数组中一般就是存放的单一的数据 而哈希表中存放的是一个键值

结构示例图:

右边是数组

数组的每个成员包括一个指针,指向一个链表的头,当然这个链表可能为空,也可能元素很多

最后

自我介绍一下,小编13年上海交大毕业,曾经在小公司待过,也去过华为、OPPO等大厂,18年进入阿里一直到现在。

深知大多数初中级Android工程师,想要提升技能,往往是自己摸索成长,自己不成体系的自学效果低效漫长且无助。

因此收集整理了一份《2024年Web前端开发全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友,同时减轻大家的负担。

img

既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上Android开发知识点!不论你是刚入门Android开发的新手,还是希望在技术上不断提升的资深开发者,这些资料都将为你打开新的学习之门!

如果你觉得这些内容对你有帮助,需要这份全套学习资料的朋友可以戳我获取!!

由于文件比较大,这里只是将部分目录截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且会持续更新!
。**

深知大多数初中级Android工程师,想要提升技能,往往是自己摸索成长,自己不成体系的自学效果低效漫长且无助。

因此收集整理了一份《2024年Web前端开发全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友,同时减轻大家的负担。

[外链图片转存中…(img-Z2h8VLec-1715247776519)]

[外链图片转存中…(img-YJ4FtO5E-1715247776520)]

[外链图片转存中…(img-Bh6wAFXe-1715247776520)]

既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上Android开发知识点!不论你是刚入门Android开发的新手,还是希望在技术上不断提升的资深开发者,这些资料都将为你打开新的学习之门!

如果你觉得这些内容对你有帮助,需要这份全套学习资料的朋友可以戳我获取!!

由于文件比较大,这里只是将部分目录截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且会持续更新!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值