9
9
## 数据库的三范式是什么?
10
10
11
11
- 第一范式:强调的是列的原子性,即数据库表的每一列都是不可分割的原子数据项。
12
- - 第二范式:要求实体的属性完全依赖于主关键字。所谓完全依赖是指不能存在仅依赖主关键字一部分的属性 。
12
+ - 第二范式:要求实体的属性完全依赖于主关键字。所谓完全 依赖是指不能存在仅依赖主关键字一部分的属性 。
13
13
- 第三范式:任何非主属性不依赖于其它非主属性。
14
14
15
15
## 事务的基本要素 ACID⭐
@@ -18,15 +18,15 @@ Atomicity(原子性):事务是一个原子操作单元,其对数据的
18
18
19
19
Consistency(一致性):在事务开始之前和事务结束以后,数据库的完整性没有被破坏。
20
20
21
- Isolation(隔离性):同一时间,只允许一个事务请求同一数据 ,不同的事务之间彼此没有任何干扰。 事务隔离分为不同级别,包括读未提交(Read uncommitted)、读提交(read committed)、可重复读(repeatable read)和串行化(Serializable)。
21
+ Isolation(隔离性):同一时间,只允许一个事务操作同一数据 ,不同的事务之间彼此没有任何干扰。 事务隔离分为不同级别,包括读未提交(Read uncommitted)、读提交(read committed)、可重复读(repeatable read)和串行化(Serializable)。
22
22
23
23
Durability(持久性):事务处理结束后,对数据的修改是永久的。
24
24
25
25
## char 和 varchar 的区别是什么?
26
26
27
27
char(n) :固定长度类型,比如订阅 char(10),当你输入"abc"三个字符的时候,它们占的空间还是 10 个字节,其他 7 个是空字节。
28
28
29
- chat 优点:效率高;缺点:占用空间;适用场景:存储密码的 md5 值,固定长度的,使用 char 非常合适。
29
+ char 优点:效率高;缺点:占用空间;适用场景:存储密码的 md5 值,固定长度的,使用 char 非常合适。
30
30
31
31
varchar(n) :可变长度,存储的值是每个值占用的字节再加上一个用来记录其长度的字节的长度。
32
32
@@ -170,17 +170,17 @@ UPDATE table SET status = 1 WHERE id=1 AND status = 0;
170
170
171
171
## mysql 索引是怎么实现的?
172
172
173
- 索引是满足某种特定查找算法的数据结构,而这些数据结构会以某种方式指向数据,从而实现高效查找数据。 MySQL 中的索引,不同的数据引擎实现有所不同,但目前主流的数据库引擎的索引都是 B+ 树实现的 。
173
+ 索引是满足某种特定查找算法的数据结构,而这些数据结构会以某种方式指向数据,从而实现高效查找数据。 MySQL 中的索引,不同的数据引擎实现有所不同,但目前主流的数据库引擎的索引都是 B+ 树实现的 。
174
174
175
175
## B树和B+树的概念和区别
176
176
177
- 1)B-树的关键字和记录是放在一起的 ,叶子节点可以看作外部节点,不包含任何信息;B+树的非叶子节点中只有关键字和指向下一个节点的索引,记录只放在叶子节点中。
177
+ 1)先说一下B-树是一种多路搜索树,关键字和记录是放在一起的 ,叶子节点可以看作外部节点,不包含任何信息;B+树的非叶子节点中只有关键字和指向下一个节点的索引,记录只放在叶子节点中。
178
178
2)在B-树中,越靠近根节点的记录查找时间越快,只要找到关键字即可确定记录的存在;而B+树中每个记录的查找时间基本是一样的,都需要从根节点走到叶子节点,而且在叶子节点中还要再比较关键字。从这个角度看B-树的性能好像要比B+树好,而** 在实际应用中却是B+树的性能要好些** 。
179
179
180
180
## 为什么选择B+树作为索引结构⭐
181
181
182
182
* 因为B+树的非叶子节点不存放实际的数据,这样每个节点可容纳的元素个数比B-树多,树高比B-树小,这样带来的好处是减少磁盘访问次数。尽管B+树找到一个记录所需的比较次数要比B-树多,但是一次磁盘访问的时间相当于成百上千次内存比较的时间,因此实际中B+树的性能可能还会好些。
183
- * B+树的叶子节点使用指针连接在一起,方便顺序遍历(例如查看一个目录下的所有文件,一个表中的所有记录等) 。
183
+ * B+树的叶子节点使用指针连接在一起,方便顺序遍历和范围查询,这也是优于hash索引的地方 。
184
184
* B+树的查询效率更加稳定,每次查询的效率一样。
185
185
186
186
** Hash索引底层是哈希表** ,哈希表是一种以key-value存储数据的结构,所以多个数据在存储关系上是完全没有任何顺序关系的,所以,对于区间查询是无法直接通过索引查询的,就需要全表扫描。所以,** 哈希索引只适用于等值查询的场景** 。而B+ 树是一种多路平衡查询树,所以他的节点是天然有序的(左子节点小于父节点、父节点小于右子节点),所以对于范围查询的时候不需要做全表扫描
@@ -276,23 +276,37 @@ order by,group by或者关联查询是否使用了索引。
276
276
277
277
## sql 优化可以从哪些方面考虑?⭐
278
278
279
- 主要是从怎么** 合理创建索引 合理使用索引以防止索引失效 合理创建表字段** 这3个方面入手
279
+ 主要是从怎么** 合理创建索引 合理编写 SQL 语句和防止索引失效 合理创建表字段** 这3个方面入手
280
280
281
- * ** 合理创建索引:**
281
+ * ** 合理创建索引:**
282
282
283
- * 对查询进行优化,要尽量避免全表扫描,首先应考虑在 where 及 order by 涉及的列上建立索引。
283
+ * ** 合理编写 SQL 语句: **
284
284
285
- * ** 防止索引失效: **
285
+ 不使用 select * ,使用 LIMIT 语句来限制返回的数据,IN包含的值不应过多等
286
286
287
- 参考上一个问题的答案
287
+ * ** 防止索引失效: ** 保证最左前缀法则,尽量不适用前缀模糊查询 %like,避免索引列参与计算或使用了函数,避免在where子句中对字段进行null值判断,看看表编码,表字段是否一样,联合索引中范围查询会让后面的索引字段失效,join查询时要用小表驱动大表
288
288
289
289
* ** 合理创建表字段:** 最好不要给数据库留NULL,尽可能的使用 NOT NULL填充数据库
290
290
291
- * 不使用 * ,使用 LIMIT 语句来限制返回的数据
291
+ ## 索引的使用经验
292
292
293
- * 减少交互次数(批量提交)
293
+ 创建索引考虑几个因素:
294
294
295
- ## ** 批量往mysql导入1000万数据有什么方法?**
295
+ 覆盖索引:因为覆盖索引可以减少回表的次数,而且在MySQL5.6后增加了一个索引下推的功能,可以在让覆盖索引配合索引下推,尽量减少回表的次数。
296
+
297
+ 可以explain命令查看执行计划时看到 extra 列的 using index condition 是说明用到了索引, Using filesort,Using temporary 都是不好的,看rows 列可以知道扫描的行数,可以根据这个判断是否需要优化。
298
+
299
+ 我们可以考虑在读少写多的场景下(日志,账单),我们可以使用普通索引,因为innodb对普通索引做了优化,使用了 ** Change buffer** ,它可以把写操作缓存下来,在读的时候再去merge,这样可以减少io次数,提高语句执行速度,提高内存利用率。
300
+
301
+ 还可以考虑索引统计信息是否有问题,analyze table重新统计信息,因为索引信息并不是一个准确值,是一个随机采样的过程。如果发现执行计划中的key列使用的索引不好时,应急预案可以考虑使用 force index 强制索引
302
+
303
+ ## 数据库调优经验
304
+
305
+ 使用了索引却仍然不是很快,就使用 explain 分析了一下发现表中有多个索引,因为可能涉及回表,排序的操作,MySQL 优化器选用了错误的索引导致查询效率偏低,然后通过 SQL 语句中使用 useindex 来指定索引解决。
306
+
307
+
308
+
309
+ ## 批量往mysql导入1000万数据有什么方法?
296
310
297
311
* 减少IO次数
298
312
0 commit comments