常见面试题之MySQL篇

news2024/11/8 23:33:39

1.MySQL中,如何定位慢查询?

我们当时做压测的时候有的接口非常的慢,接口的响应时间超过了2秒以上,因为我们当时的系统部署了运维的监控系统Skywalking,在展示的报表中可以看到是哪一个接口比较慢,并且可以分析这个接口哪部分比较慢,这里可以看到SQL的具体的执行时间,所以可以定位是哪个sql出了问题。

如果,项目中没有这种运维的监控系统,其实在MySQL中也提供了慢日志查询的功能,可以在MySQL的系统配置文件中开启这个慢日志的功能,并且也可以设置SQL执行超过多少时间来记录到一个日志文件中,我记得上一个项目配置的是2秒,只要SQL执行的时间超过了2秒就会记录到日志文件中,我们就可以在日志文件找到执行比较慢的SQL了。

2.那这个SQL语句执行很慢, 如何分析呢?

如果一条sql执行很慢的话,我们通常会使用mysql自动的执行计划explain来去查看这条sql的执行情况,比如在这里面可以通过keykey_len检查是否命中了索引,如果本身已经添加了索引,也可以判断索引是否有失效的情况,第二个,可以通过type字段查看sql是否有进一步的优化空间,是否存在全索引扫描或全盘扫描,第三个可以通过extra建议来判断,是否出现了回表的情况,如果出现了,可以尝试添加索引或修改返回字段来修复。

3.了解过索引吗?(什么是索引?)

索引在项目中还是比较常见的,它是帮助MySQL高效获取数据的数据结构,主要是用来提高数据检索的效率,降低数据库的IO成本,同时通过索引列对数据进行排序,降低数据排序的成本,也能降低了CPU的消耗。

4.索引的底层数据结构了解过嘛 ?

MySQL的默认的存储引擎InnoDB采用的B+树的数据结构来存储索引,选择B+树的主要的原因是:第一阶数更多,路径更短,第二个磁盘读写代价B+树更低,非叶子节点只存储指针,叶子阶段存储数据,第三是B+树便于扫库和区间查询,叶子节点是一个双向链表。

5.B树和B+树的区别是什么呢?

B-树,这里的 B 表示 balance( 平衡的意思),B-树是一种多路自平衡的搜索树(B树是一颗多路平衡查找树)。

在这里插入图片描述

B+树是B-树的变体,也是一种多路搜索树。
在这里插入图片描述

区别:

第一:在B树中,非叶子节点和叶子节点都会存放数据,而B+树的所有的数据都会出现在叶子节点,在查询的时候,B+树查找效率更加稳定;

第二:在进行范围查询的时候,B+树效率更高,因为B+树都在叶子节点存储,并且叶子节点是一个双向链表。

6.什么是聚簇索引?什么是非聚簇索引?

聚簇索引主要是指数据与索引放到一块,B+树的叶子节点保存了整行数据,有且只有一个,一般情况下主键在作为聚簇索引的;

非聚簇索引值的是数据与索引分开存储,B+树的叶子节点保存对应的主键,可以有多个,一般我们自己定义的索引都是非聚簇索引。

7.知道什么是回表查询嘛 ?

嗯,其实跟刚才介绍的聚簇索引和非聚簇索引是有关系的,回表的意思就是通过二级索引找到对应的主键值,然后再通过主键值找到聚集索引中所对应的整行数据,这个过程就是回表。

在这里插入图片描述

备注:如果面试官直接问回表,则需要先介绍聚簇索引和非聚簇索引】

8.知道什么叫覆盖索引嘛 ?

覆盖索引是指select查询语句使用了索引,在返回的列,必须在索引中全部能够找到,如果我们使用id查询,它会直接走聚集索引查询,一次索引扫描,直接返回数据,性能高。

如果按照二级索引查询数据的时候,返回的列中没有创建索引,有可能会触发回表查询,尽量避免使用select *,尽量在返回的列中都包含添加索引的字段。

9.MYSQL超大分页怎么处理 ?

超大分页一般都是在数据量比较大时,我们使用了limit分页查询,并且需要对数据进行排序,这个时候效率就很低,我们可以采用覆盖索引和子查询来解决。

先分页查询数据的id字段,确定了id之后,再用子查询来过滤,只查询这个id列表中的数据就可以了。

因为查询id的时候,走的覆盖索引,所以效率可以提升很多。

10.索引创建原则有哪些?

就是表中的数据要超过10万以上,我们才会创建索引,并且添加索引的字段是查询比较频繁的字段,一般也是像作为查询条件,排序字段或分组的字段这些。

还有就是,我们通常创建索引的时候都是使用复合索引来创建,一条sql的返回值,尽量使用覆盖索引,如果字段的区分度不高的话,我们也会把它放在组合索引后面的字段。

如果某一个字段的内容较长,我们会考虑使用前缀索引来使用,当然并不是所有的字段都要添加索引,这个索引的数量也要控制,因为添加索引也会导致新增改的速度变慢。

11.什么情况下索引会失效 ?

比如,索引在使用的时候没有遵循最左匹配法则,第二个是,模糊查询,如果%号在前面也会导致索引失效。如果在添加索引的字段上进行了运算操作或者类型转换也都会导致索引失效。

我们之前还遇到过一个就是,如果使用了复合索引,中间使用了范围查询,右边的条件索引也会失效。

所以,通常情况下,想要判断出这条sql是否有索引失效的情况,可以使用explain执行计划来分析。

12.sql的优化的经验?

如果直说sql优化的话,我们会从这几方面考虑,比如:

建表的时候、使用索引、sql语句的编写、主从复制,读写分离,还有一个是如果量比较大的话,可以考虑分库分表。

13.创建表的时候,你们是如何优化的呢?

  1. 尽量选择小的数据类型,数据类型选择上尽量tinyint(1字节)>smallint(2字节)>int(4字节)>bigint(8字节),比如逻辑删除y/n字段上(1代表可用,0代表)就可以选择tinyint(1字节)类型;
  2. 尽量保证字段数据类型长度固定;
  3. 尽量避免使用null,使用null的字段查询很难优化,影响索引,可以使用0或''代替;
  4. 避免宽表,能拆分就拆分,一个表往往跟一个实体域对应,就像设计对象的时候一样,保持单一原则;
  5. 尽量避免使用textblob,如果非使用不可,将类型为textblob的字段在独立成一张新表,然后使用主键对应原表;
  6. 禁止使用floatdouble类型,这个坑超大,floatdouble存在精度问题,在进行比较或者加减操作的时候会丢失精度导致数据异常,凡是使用floatdouble类型的时候考虑下可不可使用intbigint代替。比如金额,以元为单位使用floatdouble类型的时候,可以考虑以分为单位使用intbigint类型代替,然后由业务代码进行单位的转换;
  7. 每张表都加上createUsercreateTimeupdateUserupdateTime字段;
  8. 起名字要规范,包括:库名,表名,字段名,索引名;
  9. 查询频繁使用的字段记得加索引;
  10. 尽量避免使用外键,不用外键约束,性能更高,然后数据的完整性有程序进行管理;
  11. 如果表的数量可以预测到非常大,最好在建表的时候,就进行分表,不至于一时间数据量非常大导致效率问题。

14.那在使用索引的时候,是如何优化呢?

  1. 维度高的列创建索引。
  2. 数据列中不重复值出现的个数,这个数量越高,维度就越高。
  3. 如数据表中存在8行数据a,b ,c,d,a,b,c,d这个表的维度为4。
  4. 要为维度高的列创建索引,如性别和年龄,那年龄的维度就高于性别。
  5. 性别这样的列不适合创建索引,因为维度过低。
  6. where,on,group by,order by中出现的列使用索引。
  7. 对较小的数据列使用索引,这样会使索引文件更小,同时内存中也可以装载更多的索引键。
  8. 为较长的字符串使用前缀索引。
  9. 不要过多创建索引,除了增加额外的磁盘空间外,对于DML操作的速度影响很大,因为其每增删改一次就得从新建立索引。
  10. 使用组合索引,可以减少文件索引大小,在使用时速度要优于多个单列索引。

15.你平时对sql语句做了哪些优化呢?

  1. 查询的时候一定要记得使用limit进行限制
  2. 对于结果只需要一条数据的查询用limit 1进行限制
  3. 使用count(*)来统计行数或者使用count(主键)来查询,使用count(列)的时候,不会统计此列为null的情况
  4. 不要使用select * 来查数据,使用select需要的列名,这样的方式去查询
  5. 使用join链接代替子查询
  6. 不要使用外键,外键的约束可以放在程序里解决
  7. 控制一下in操作的集合数量,不要太大了
  8. 针对慢查询使用explain去分析原因,然后优化sql,让其尽量走索引
  9. 注意SQL语句避免造成索引失效的写法;
  10. 如果是聚合查询,尽量用union all代替unionunion会多一次过滤,效率比较低;
  11. 如果是表关联的话,尽量使用inner join ,不要使用用left joinright join,如必须使用 一定要以小表为驱动。

16.事务的特性是什么?可以详细说一下吗?

这个比较清楚,事务的特性:ACID,分别指的是:原子性、一致性、隔离性、持久性;

我举个例子:

A向B转账500,转账成功,A扣除500元,B增加500元,原子操作体现在要么都成功,要么都失败;

在转账的过程中,数据要一致,A扣除了500,B必须增加500;

在转账的过程中,隔离性体现在A像B转账,不能受其他事务干扰;

在转账的过程中,持久性体现在事务提交后,要把数据持久化(可以说是落盘操作)。

17.并发事务带来哪些问题?

我们在项目开发中,多个事务并发进行是经常发生的,并发也是必然的,有可能导致一些问题。

第一是脏读, 当一个事务正在访问数据并且对数据进行了修改,而这种修改还没有提交到数据库中,这时另外一个事务也访问了这个数据,因为这个数据是还没有提交的数据,那么另外一个事务读到的这个数据是“脏数据”,依据“脏数据”所做的操作可能是不正确的。

第二是不可重复读:比如在一个事务内多次读同一数据。在这个事务还没有结束时,另一个事务也访问该数据。那么,在第一个事务中的两次读数据之间,由于第二个事务的修改导致第一个事务两次读取的数据可能不太一样。这就发生了在一个事务内两次读到的数据是不一样的情况,因此称为不可重复读。

第三是幻读(Phantom read):幻读与不可重复读类似。它发生在一个事务(T1)读取了几行数据,接着另一个并发事务(T2)插入了一些数据时。在随后的查询中,第一个事务(T1)就会发现多了一些原本不存在的记录,就好像发生了幻觉一样,所以称为幻读。

18.并发事务怎么解决这些问题呢?MySQL的默认隔离级别是?

解决方案是对事务进行隔离。

MySQL支持四种隔离级别,分别有:

第一个是,未提交读(read uncommitted)它解决不了刚才提出的所有问题,一般项目中也不用这个。第二个是读已提交(read committed)它能解决脏读的问题的,但是解决不了不可重复读和幻读。第三个是可重复读(repeatable read)它能解决脏读和不可重复读,但是解决不了幻读,这个也是mysql默认的隔离级别。第四个是串行化(serializable)它可以解决刚才提出来的所有问题,但是由于让是事务串行执行的,性能比较低。所以,我们一般使用的都是mysql默认的隔离级别:可重复读。

19.undo logredo log的区别?

其中redo log日志记录的是数据页的物理变化,服务宕机可用来同步数据,而undo log不同,它主要记录的是逻辑日志,当事务回滚时,通过逆操作恢复原来的数据,比如我们删除一条数据的时候,就会在undo log日志文件中新增一条delete语句,如果发生回滚就执行逆操作;

redo log保证了事务的持久性,undo log保证了事务的原子性和一致性。

在这里插入图片描述

在这里插入图片描述

20.事务中的隔离性是如何保证的呢?(你解释一下MVCC)

事务的隔离性是由锁和mvcc实现的。

其中mvcc的意思是多版本并发控制。指维护一个数据的多个版本,使得读写操作没有冲突,它的底层实现主要是分为了三个部分,第一个是隐藏字段,第二个是undo log日志,第三个是readView读视图。

隐藏字段是指:在mysql中给每个表都设置了隐藏字段,有一个是trx_id(事务id),记录每一次操作的事务id,是自增的;另一个字段是roll_pointer(回滚指针),指向上一个版本的事务版本记录地址。

undo log主要的作用是记录回滚日志,存储老版本数据,在内部会形成一个版本链,在多个事务并行操作某一行记录,记录不同事务修改数据的版本,通过roll_pointer指针形成一个链表。

readView解决的是一个事务查询选择版本的问题,在内部定义了一些匹配规则和当前的一些事务id判断该访问那个版本的数据,不同的隔离级别快照读是不一样的,最终的访问的结果不一样。如果是rc隔离级别,每一次执行快照读时生成ReadView,如果是rr隔离级别仅在事务中第一次执行快照读时生成ReadView,后续复用。

21.MySQL主从同步原理 ?

MySQL主从复制的核心就是二进制日志(DDL(数据定义语言)语句和DML(数据操纵语言)语句),它的步骤是这样的:

第一:主库在事务提交时,会把数据变更记录在二进制日志文件Binlog中。

第二:从库读取主库的二进制日志文件Binlog,写入到从库的中继日志Relay Log

第三:从库重做中继日志中的事件,将改变反映它自己的数据。

22.你们项目用过MySQL的分库分表吗?

因为我们都是微服务开发,每个微服务对应了一个数据库,是根据业务进行拆分的,这个其实就是垂直拆分。

23.那你之前使用过水平分库吗?

这个是使用过的,我们当时的业务是(xxx),一开始,我们也是单库,后来这个业务逐渐发展,业务量上来的很迅速,其中(xx)表已经存放了超过1000万的数据,我们做了很多优化也不好使,性能依然很慢,所以当时就使用了水平分库。

我们一开始先做了3台服务器对应了3个数据库,由于库多了,需要分片,我们当时采用的mycat来作为数据库的中间件。数据都是按照id(自增)取模的方式来存取的。

当然一开始的时候,那些旧数据,我们做了一些清洗的工作,我们也是按照id取模规则分别存储到了各个数据库中,好处就是可以让各个数据库分摊存储和读取的压力,解决了我们当时性能的问题。

24.MySQL支持哪些存储引擎?

MySQL支持多种存储引擎,比如InnoDBMyISAMMemoryArchive等等.在大多数的情况下,直接选择使用 InnoDB 引擎都是最合适的,InnoDB也是MySQL的默认存储引擎。

MyISAMInnoDB的区别有哪些:

  • InnoDB支持事务,MyISAM不支持
  • InnoDB支持外键,而MyISAM不支持
  • InnoDB是聚集索引,数据文件是和索引绑在一起的,必须要有主键,通过主键索引效率很高;MyISAM是非聚集索引,数据文件是分离的,索引保存的是数据文件的指针,主键索引和辅助索引是独立的。
  • Innodb不支持全文索引,而MyISAM支持全文索引,查询效率上MyISAM要高;
  • InnoDB不保存表的具体行数,MyISAM用一个变量保存了整个表的行数。
  • MyISAM采用表级锁(table-level locking);InnoDB支持行级锁(row-level locking)和表级锁,默认为行级锁。

25.超键、候选键、主键、外键分别是什么?

超键:在关系中能唯一标识元组的属性集称为关系模式的超键。一个属性可以为作为一个超键,多个属性组合在一起也可以作为一个超键。超键包含候选键和主键。
候选键:是最小超键,即没有冗余元素的超键。
主键:数据库表中对储存数据对象予以唯一和完整标识的数据列或属性的组合。一个数据列只能有一个主键,且主键的取值不能缺失,即不能为空值(Null)。
外键:在一个表中存在的另一个表的主键称此表的外键。

26.SQL约束有哪几种?

NOT NULL: 用于控制字段的内容一定不能为空(NULL)。
UNIQUE: 控件字段内容不能重复,一个表允许有多个Unique约束。
PRIMARY KEY: 也是用于控件字段内容不能重复,但它在一个表只允许出现一个。
FOREIGN KEY: 用于预防破坏表之间连接的动作,也能防止非法数据插入外键列,因为它必须是它指向的那个表中的值之一。
CHECK: 用于控制字段的值范围。

27.MySQL中的varcharchar有什么区别?

char是一个定长字段,假如申请了char(10)的空间,那么无论实际存储多少内容。该字段都占用 10 个字符,而 varchar是变长的,也就是说申请的只是最大长度,占用的空间为实际字符长度+1,最后一个字符存储使用了多长的空间。

在检索效率上来讲,char > varchar,因此在使用中,如果确定某个字段的值的长度,可以使用char,否则应该尽量使用 varchar。例如存储用户MD5加密后的密码,则应该使用char

28.MySQLinexists区别?

MySQL中的in语句是把外表和内表作hash连接,而exists语句是对外表作loop循环,每次loop循环再对内表进行查询。一直大家都认为existsin语句的效率要高,这种说法其实是不准确的。这个是要区分环境的。

如果查询的两个表大小相当,那么用inexists差别不大。
如果两个表中一个较小,一个是大表,则子查询表大的用exists,子查询表小的用in
not innot exists:如果查询语句使用了not in,那么内外表都进行全表扫描,没有用到索引;而not extsts的子查询依然能用到表上的索引。所以无论那个表大,用not exists都比not in要快。

29. dropdeletetruncate的区别?

三者都表示删除,但是三者有一些差别:
在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/677933.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【数据库七】MySQL主从复制与读写分离

MySQL主从复制与读写分离 1.案例概述2.什么是读写分离?3.为什么要读写分离呢?4.什么时候要读写分离?5.主从复制与读写分离6.MySQL主从复制原理6.1 mysql的复制类型 7.主从复制的工作过程7.1 MySQL架构图7.2 口语化工作工程 8.MySQL 读写分离原…

VSCode配置C语言编译环境

一、下载C语言编译器: (1)下载地址:MinGW-w64 - for 32 and 64 bit Windows - Browse /mingw-w64 at SourceForge.net 下载如下的windows版本: (2)配置环境变量: 二、安装VSCode …

Linux学习[18]bash学习深入4----命令执行的判断依据---【; , , ||】---用于一次性输入多指令情况

文章目录 前言判断符号 ;判断符号 &&与||总结 前言 使用指令的时候,使用完一个指令之后,我想让它接着执行另一个指令,而非等A指令执行完之后再输入B指令。 为了实现这个效果,我查阅了相关资料,这里…

【从零开始学习JAVA | 第十六篇】杂项知识点介绍

目录 前言: 包: final: 权限修饰符: 总结: 前言: 本文不隶属于正文序列,而是对面向对象中的一些常用词进行介绍,方便大家理解记忆,本文将会逐一介绍 什么是包,final…

云服务器部署企业版openGauss

openGauss 企业版安装 教程 1.下载安装包 在华为云上租一台服务器,操作系统选:openEuler 20.03 64bit (64-bit) 获取openGauss Server安装包,企业版:软件包链接 使用xshell连接服务器,准备软硬件安装环境(该装的依…

【软件架构模式】—微内核架构

欢迎回到软件架构模式博客系列。这是本系列的第 4 章,我们将讨论微内核架构模式 概述: 内核模式也被称为插件架构模式。将附加应用程序功能作为插件添加到核心应用程序,以提供可扩展性以及功能分离和隔离。 这种模式由两种类型的架构组件组…

如何搭建LNMP架构

目录 一、什么是LNMP Linux系统 Apache服务 Nginx服务 MySQL数据库 PHP服务 二、搭建LNMP 安装Nginx服务 第一步 关闭防火墙和安全机制 第二步 安装依赖环境 第三步 创建运行用户 第四步 解压服务包 第五步 编译安装 第六步 编译 第八步 添加 Nginx 系统服务 …

leetcode63. 不同路径 II(动态规划-java)

不同路径 II leetcode63. 不同路径 II题目描述暴力递归代码演示动态规划代码演示 动态规划空间压缩 动态规划专题 leetcode63. 不同路径 II 来源:力扣(LeetCode) 链接:https://leetcode.cn/problems/unique-paths-ii 题目描述 一个…

自然图像中的字符识别:Chars74K 数据集

字符识别是 研究人员从计算机早期开始工作 视觉。随着当今相机的无所不在,应用 的自动字符识别比以往任何时候都更广泛。为 拉丁字母,这在很大程度上被认为是一个已解决的问题 受限情况,例如扫描文档的图像 包含常用字符字体和统一 背景。但是…

7.4_3B+树

特点:块内无序,块间有序(类比于分块查找) 这个性质是为了追求平衡 3)结点的子树个数与关键字个数相等 4)所有叶节点包含全部关键字及指向相应记录的指针,叶节点中将关键字按照大小顺序排列, 并且相邻叶节点…

Camera之android8.0以上HIDL与C++数据类型转换(三十)

简介: CSDN博客专家,专注Android/Linux系统,分享多mic语音方案、音视频、编解码等技术,与大家一起成长! 优质专栏:Audio工程师进阶系列【原创干货持续更新中……】🚀 人生格言: 人生从来没有捷径,只有行动才是治疗恐惧和懒惰的唯一良药. 更多原创,欢迎关注:Android…

rust 集合、错误处理、泛型、Trait、生命周期、包

集合组织特性相同的数据;泛型可以定义任何抽象数据类型;生命周期限制所有权的作用域范围;错误处理使程序更健壮。 集合 一组特性相同的数据集合,除了基本数据类型的元组、数组。rust 标准库提供了一些非常有用的数据结构。 Vec…

Redis从入门到精通【进阶篇】之高可用主从详解

文章目录 0.前言1.详解1.1 主从复制概述1.2 主从复制原理1.2.1.全量复制1.2.2.增量复制1.2.3.详细描述1.3 更深入理解1.4 常见面试题 2. 总结3. Redis从入门到精通系列文章 0.前言 Redis是一个高性能的键值存储系统,广泛应用于Web应用、缓存、消息队列等领域。在实…

C++【STL】之priority_queue学习

优先级队列 优先级队列priority_queue也是STL库中容器适配器的一种,常用于进行数据优先级的处理,说到这儿是不是发现有些熟悉,没错它和我们之前讲解的堆本质上就是一个东西,底层都是数组存储的完全二叉树,它在STL库中…

零基础速成simulink代码生成——DBC文件CAN报文+stateflow 5

零基础速成simulink代码生成——DBC文件CAN报文+stateflow 5 上一篇文章中,已经实现将dbc文件进行代码生成,这边我们要实现一个功能,添加多几个can报文分时发送,结合statflow简单实现这个功能。 添加报文 我们还是选用相同的can报文添加 选中所有的模块,ctrl+c。 ctrl+…

InvPT++:用于视觉场景理解的倒金字塔多任务Transformer

文章目录 InvPT: Inverted Pyramid Multi-Task Transformer for Visual Scene Understanding摘要本文方法整体结构InvPT EncoderTask-Specific Preliminary DecodersStructure of InvPT DecodeUP-Transformer BlockCross-Scale Self-Attention: Fusion Attention and Selective…

团体程序设计天梯赛-练习集L1篇⑦

🚀欢迎来到本文🚀 🍉个人简介:Hello大家好呀,我是陈童学,一个与你一样正在慢慢前行的普通人。 🏀个人主页:陈童学哦CSDN 💡所属专栏:PTA 🎁希望各…

ChatGPT | LangChain的文本切割方法对比

本文来自http://blog.csdn.net/hellogv/ ,引用必须注明出处! ChatGPT面向对话格式的文本理解很好,但如果要把网络上的文章让ChatGPT直接分析则会有格式的问题。文本清洗是个大课题,讲起来需要很多篇幅,优化起来前路漫…

学习C++的意义

文章目录 前言意义软件方法论的发展面向对象的程序设计宽泛的意义 C到C的升级ubuntu安装g编译器总结 前言 C是一种强大而广泛应用的编程语言,具有广泛的用途和应用领域。无论你是计算机科学专业的学生、自学编程的爱好者,还是想要进一步提升编程技能的专…

在linux系统中如何设置定时任务

前言: 在linux日常运维过程中我们常常需要在指定时间段自动停止或启动某个服务我们不可能人为的手动去执行,这时候我们就可以给对应的任务设置一个定时。后面我就可以将周期性的、规则的工作交给定时任务去完成。 **一次性任务:**顾名思义就是…