文章目录
1.事务
1.事务的特性 ACID
2.并发事务问题
脏读:一个事务读到了另一个事务还没有提交的数据 解决:读已提交
不可重复读:事务A先读一条数据,然后再读这条数据发现被改了 解决:可重复读
幻读:事务A读取数据时,发现没有对应的数据行,准备插入时发现这行数据已经存在了 解决:串行化
3.undo log 和redo log的区别?
undo log是回滚日志,记录的是数据库的逆操作,比如插入一条数据,记录的其实是删除一条数据,用来做回滚的。
redo log是重做日志,记录的是数据页的物理变化,用于宕机时进行数据恢复的。
4.事务的隔离性是如何保证的呢?解释一下MVCC?
主要有三个方面,隐藏字段,undo log版本链,readView
隐藏字段:有最近修改事务id,回滚指针
undo log版本链:就是多个事务同时修改一条记录时,会通过回滚指针和undo log日志形成一条链表
readView:读视图,根据一些匹配规则来决定要读取哪个版本的数据,对于不同的事务隔离级别快照读是不同的,访问结果也是不一样的,比如读已提交每次读的时候都会生成一个readView,而可重复读只有第一次读的时候才生成readView
2.索引
1.如何定位慢查询?
首先要通过请求的时间去判断这个接口的响应速度是不是正常的。
接下来可以使用运维工具skywalking,检测出慢查询的SQL。
也可以在mysql中开启慢日志查询,记录慢查询的SQL。
2.explain
主要有四个参数:可能用到的索引,实际用到的索引,索引长度以及额外的优化建议。
可以根据实际用到的索引以及索引长度去判断是否有索引失效了,然后可以根据额外字段的信息去优化,比如Using index condition就是使用了索引,但是需要回表查询数据,最后就是通过类型去分析,避免索引树扫描和全盘扫描。
3.了解过索引吗?索引的底层数据结构B树和B+树对比
索引底层是使用B+树来实现的,就是一个数据结构,用于增加SQL查询速度的一个手段。
B树中的每个节点都存储键和数据,然后B+树除了叶子节点都是存键的,只有叶子结点才存储实际数据,并且是一个双向链表,方便扫库和区间扫描,而且阶数更多,路径更短。
4.什么是聚集索引,什么是二级索引?
聚集索引的选举规则:按照主键、第一个唯一索引,隐藏字段中的rowid的顺序进行选举
聚集索引就是B+树的叶子节点存储的是id和整行数据(只有一个),二级索引是存储的二级索引的值以及id值(可以有多个)
5.什么是回表查询?
假设id,name,age,其中name是二级索引,如果根据name查询id,name就不会回表,因为二级索引中可以直接查询出来,但是如果还要查询age,那么就需要从二级索引中查询出id,然后用这个id去聚集索引中查询整行数据,从中得到age。
6.什么叫覆盖索引?
覆盖索引就是查询使用了索引,然后需要返回的列使用这个索引全部都能找到。比如id,name,age,name是二级索引,直接使用name查询id和name就是覆盖索引。
7.MySQL超大分页处理,使用覆盖索引+子查询临时表
8.索引创建的原则
原则有很多,但是有一个前提是这张表的数据量必须要足够大,比如单表10万条数据,然后对于常作为查询条件的字段,比如where,group by,order by的字段才要考虑加索引,并且要控制索引的数量,因为索引只是增加查询效率,会影响增删改的效率,尽量使用联合索引,因为很多时候可以覆盖索引。
9.索引失效的情况
1.违反最左前缀法则
2.范围查询时右边的列,不能使用索引
3.索引列进行运算操作,索引将失效
4.字符串不加单引号,索引失效
5.头部模糊查询会导致索引失效,最后的一个元素模糊,则索引不会失效
6.or连接的条件,前面的列有索引,后面的列没有索引,那么涉及到的索引都不会被用到
3.SQL优化
1.SQL怎么优化?
首先在设计表的时候要选择合适的字符串类型,比如定长的字段就使用char,不要使用varchar,效率较低
然后在SQL语句方面,查询的时候一定要指定字段名称,不要使用select *,避免索引失效的写法,使用union all代替union,再就是join的优化了,能用inner join 就不要用left right join 如果必须使用一定要小表驱动,减少大表的扫描次数。
2.union all 与union的区别
union all是直接将结果合并,可以包含重复数据
union 是将结果合并,并过滤掉重复数据,会多一次过滤