MySQL的索引和事务

索引

索引的概念

那索引是啥呢?
类似于目录 也是一种特殊的文件,能够提高查询的速度,但也会占用更多的空间,也可以会减慢增删查改的速度. 在数据库中索引可以分为很多种类型,比如B树索引 哈希索引、位图索引等等 。每种索引类型适用于不同类型的数据和查询优化。比如:B树索引适用于范围查询和顺序访问;哈希索引则适用等值查询和快速访问。

索引的意义

索引最大的意义就是在于提高数据访问的效率。打个比方 如果我们现在想要查找一个特定的数据项,我们要遍历整个数据集合 这样的查询是十分低效的;但我们有了索引之后,就可以直接通过索引定位到数据的位置,这样就大幅度提高了查找的效率。

索引的使用

我们了解索引之后,该如何使用索引呢
1、查看索引 show index from 表名
2、创建索引 create index 索引名 on 表名(列名)
3、删除索引 drop index 索引名 on 表名
在这里我们需要注意的是 删除索引的操作也是一个非常危险的操作 这里的操作都会涉及到大量的IO操作,就很有可能把MySQL主机给搞挂了。

索引底层的数据结构

那索引背后的数据结构是什么呢 二叉树 吗 还是其他的
用来查询对比数据结构其实有很多 包括二叉搜索树(红黑树)、哈希表

红黑树 并不适用于大量的大规模的硬盘上管理数据的场景。为什么呢
**原因:**红黑树是二叉搜索树 ,当元素很多的时候,就会让树的高度变得比较高,树的高度越高 进行查询的速度就会越低 比如说你在中序遍历找到下一个后继节点这样的操作,很有可能要往父节点上进行一系列回溯,才能够找到该节点 高度每增加一层,比较次数就加1 比较操作就会需要一次IO操作了 。

哈希表也不行 虽然哈希表每次查找的速度都是O(1),但哈希表只能查找相等的 相等的才能进行判断 不能判断其他情况 不能进行范围查找。

总的来说 ,最适合做索引的 还得是树型结构 你想想 红黑树 是因为树的高度为高了就会降低查找的速度 那我们如果让树多分几个叉出来 那树的高度不就自然而然的下降了吗。 所以我们可以引入‘多叉搜索时’ 这样的数据结构就是 B+树。

要想了解B+树 我们先了解一下B树 本质上是一个N叉搜索树
每个节点上可以存储多个元素,延申出多个字数。
表示同样数量的数据,需要的节点就少了,对应的树的高度也就大幅度降低了。

在这里插入图片描述
如上图 这就是B树的基本模型。

在这里拿着一个key在某个节点比较的时候,确实也是需要更多的次数 也不是一次比较就完成的 但是这里的比较 还是有说法的。
1、每个节点上的key都是有序排列的,比较的时候可以使用二分查找。
2、B树也会控制,某个节点上保存的key不会太多
3、多个数据,都是放在一块存储空间上的,进行比较的时候,一次硬盘IO操作就能读出整个节点。虽然有多次比较 但只进行一次硬盘IO。

那B+树是怎么样的呢
其实B+树就是B树的升级版
在这里插入图片描述
B+树,会把叶子节点通过类似于链表这样的链式结构串起来,此时就可以通过上诉链式结构非常方便的遍历整个表中的所有数据了 。

B+ 树相对于B树的优势在哪呢
1、非常方便进行遍历和范围查询
2、当前任何一次查询操作,最终都会落到叶子节点完成的,查询任何数据经历的IO操作都是一样的 这个时候,查询操作消耗的时间是非常稳定的。
3、由于叶子节点,是数据的全几,对应的,非叶子节点中,都是重复出现的数据;就可以把表每一行的数据,最终关联到叶子节点这一层,非叶子节点中只保存一个单纯的key值即可。

而且B+树这个结构会一直存在的,如果你定义了主键,自然索引就按照主键来建立 ,如果没定义主键,会有自带的隐藏的列建立。

事务

概念

事务就是为了把多个独立的操作打包成一个整体。
在日常开发中,很多操作,不是通过一个SQL 就可以完成的,往往需要多个SQL配合完成。当执行多个SQl操作的时候,如果中间出现了特殊的情况(网络断开、系统崩溃 等等)可能会导致 前面的SQL执行完成了 但是后面的SQL执行失败了。
会出现什么场景呢 就会有 你给我转账 你的钱减少了 但是我的钱并没有增加 这种转账丢失的情况是十分严重的 涉及到财产安全问题.

事务的特性

原子性

原子性是指事务是一个不可分割的工作单位,事务的操作要么全部成功 ,要么就失败。事务中的若干个sql是一条一条执行的,事务可以保证当执行到哪一条出现问题时,数据库就会自动回滚到到一开始 重新执行一次。

一致性

一致性是数据库执行事务之前和执行事务之后 保证数据是一致的 不会出现对不上的情况 。 这也和回滚机制有关 一旦触发回滚机制回来 回滚回去的数据都是正确的 没有触发回滚机制 数据也是正确的。

持久性

持久性是指一旦事务提交,则事务所做的修改就会永久保存到数据库中,即使发生故障 网络断开、系统崩溃 数据也不会丢失。

隔离性

隔离性是指 当一个事务执行的时候 不受其他并发事务的影响 就类似多个客户端同时给服务器发起事务 系统就应该确保该事务和其他事务隔离起来,防止造成冲突。

上面事务的四个特性共同保证了数据库的稳定性和可靠性 能让数据库在并发环境下稳定运行。

并发执行事务会带来的问题

脏读问题

脏读问题就是说现在有事务A和事务B 事务A现在针对某个表做出了一些修改,在事务A提交之前 ,事务B就对这里的数据进行了读取,最终就可能出现A后续的操作又把上面的数据进行了 修改 导致B读到的数据和A提交的数据是不一样的。

举个例子:
假如我在备课,在写一些代码 ,就有些同学路过的时候,偷偷的瞄了一眼我的屏幕,看到了我写的代码 ,偷偷的记下来。我虽然是写了 这些代码 但是可能在同学看完,走了之后,我把代码修改了 最终可能我上课的时候的代码和同学瞄的代码是不一样的。这时该同学就读到了一个“临时数据” 这个临时数据 也被称为脏数据

那该怎么解决脏读问题呢?
可以针对“写操作”进行加锁,我在写的时候就不能进行读 写完了才能读
就相当于 并发执行的时候 事务A和事务B是可以同时执行的,现在引入了写加锁之后,执行A的过程,B就不能执行了 要等待A执行完。
这样就降低了‘并发能力’,提高了隔离性,提高了数据的准确性。

不可重复读问题

如果一个事务中有多个读的操作,多次读操作 读出来的结果不一致。

就相当于现在有三个事务ABC
事务A针对数据进行修改提交,接下来事务B进行读取操作 这里事务B多个SQL都要进行读操作 在执行B的过程中 有个C事务又针对数据进行了修改,就会让B里面的不同读操作 ,读出来的结果是不一样的。
那该如何解决不可重复读操作呢
给读操作也加锁 我写的时候别人也不能读,别人读的时候我也不能写 。这样我们引入了读操作的加锁 就会让并发性又下降了 ‘隔离性’又进一步的提高了。

幻读问题

现在事务A先修改并提交数据 ,事务B进行读数据,此时事务C,没有修改事务B读的数据,但是给对应的表进行了新增数据或者删除数据的操作 事务B中读到的数据集不一样 但是已有的数据内容是一致的 数据的条数增加或者减少。

要解决幻读操作 让事务“串行化执行” 使所有事务都严格按照“一个接一个的执行” ,完全没有并发了,此时执行的效率是最低的 隔离性也是最高的 数据也是最准确的。

上面的事务和索引 的内容在面试中是经常问到的 事务的四大特性很重要 尤其是隔离性 是最难理解的 上面的=说明 并发性和隔离性 不能两者兼得的 要根据实际情况来调整数据库的隔离级别 控制并发性。

好了上诉就是本篇博客的所有内容了 谢谢大家的浏览 !!!

  • 28
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值