那些年把我问懵的MySQL面试题(血泪经验版)

“同学,能说说MySQL事务的隔离级别吗?”
“呃…就是读未提交、读已提交…还有那个可重复读和串行化!”
“那这些隔离级别具体解决了什么问题呢?”
(当场石化)

作为面过无数大厂的过来人,今天就把MySQL面试里那些高频必杀题掰开了揉碎了讲!准备好迎接暴击了吗?(建议收藏后反复观看)


一、事务的ACID到底是啥?(必考题!)

面试官一开口问这个,我就知道他要开始挖坑了!先背标准答案:

  • Atomicity(原子性):事务要么全成功,要么全失败(比如转账不能只扣钱不加钱)
  • Consistency(一致性):数据要符合业务规则(比如账户余额不能为负)
  • Isolation(隔离性):多个事务并发时互不干扰
  • Durability(持久性):事务提交后数据永久保存

但是! 这里有个大坑:一致性到底是谁保证的?(灵魂拷问)

  • 数据库只保证原子性、隔离性、持久性
  • 一致性其实靠业务代码+数据库共同维护!(敲黑板)
    比如你非要在代码里写余额-1000不检查,数据库可不会拦着你!

二、索引优化连环炮(送命题)

2.1 为什么加了索引还是慢?

别急着甩锅给索引!先看看这些情况你中招没:

  1. 索引字段用了函数/表达式(WHERE YEAR(create_time)=2023
  2. 隐式类型转换(varchar字段传了数字)
  3. 最左前缀失效(建了(a,b,c)索引却只用b,c条件)
  4. 回表查询太多(select * 用覆盖索引啊!)

真实案例:某电商项目查订单慢了,EXPLAIN一看——好家伙,明明有联合索引,却因为order by create_time导致filesort!(解决方法:把create_time加到联合索引最后)

2.2 10亿数据怎么快速分页?

LIMIT 1000000,10 会先查1000010条再扔掉,不慢才怪!试试这两招:

方案一

SELECT * FROM table WHERE id > 上次最大ID LIMIT 10

方案二(复杂条件):

SELECT * FROM table 
INNER JOIN (SELECT id FROM table WHERE ... LIMIT 1000000,10) AS tmp 
USING(id)

三、锁机制:死锁是怎么找上你的?

3.1 行锁升级表锁(血案现场)

当你的SQL索引失效时,行锁会直接升级为表锁!比如:

UPDATE users SET age=18 WHERE name LIKE '%王%'; 

如果name字段没索引,恭喜你——全表锁住了!

3.2 死锁名场面

事务A:

UPDATE account SET balance=100 WHERE id=1;
UPDATE account SET balance=200 WHERE id=2;

事务B:

UPDATE account SET balance=300 WHERE id=2;
UPDATE account SET balance=400 WHERE id=1;

当两个事务以不同顺序更新资源时,死锁就诞生了!(MySQL会自动检测并回滚代价小的事务)


四、灵魂拷问:MVCC原理是什么?

这个问题的杀伤力在于——很多开发者用了多年事务,却不知道底层机制!

MVCC(多版本并发控制)核心三板斧

  1. 每个事务有唯一事务ID(递增)
  2. 每行数据有DB_TRX_ID(最后更新它的事务ID)和DB_ROLL_PTR(回滚指针)
  3. ReadView机制决定能看到哪个版本的数据

举个栗子🌰:

  • 事务A(ID=100)开启,创建ReadView
  • 事务B(ID=101)更新了某行数据
  • 事务A查询时,发现该行DB_TRX_ID=101 > 自己的ReadView,就顺着回滚指针找旧版本

这就实现了可重复读隔离级别!(是不是比直接背概念清晰多了?)


五、终极难题:主从延迟怎么办?

5.1 延迟产生的原因

  1. 主库并发写入,从库单线程重放
  2. 大事务执行时间长(比如全表更新)
  3. 从库服务器配置差

5.2 解决方案大乱斗

  • 半同步复制:主库等至少一个从库收到日志再返回
  • 并行复制:MySQL 5.7后的多线程复制
  • 缓存双写:更新数据时同时写缓存
  • 强制路由:关键业务查询强制走主库(但会增加主库压力)

血泪教训:某金融项目因为主从延迟导致用户看到"余额消失",最后只能用SHOW SLAVE STATUS查延迟,关键操作全部切主库查询!


六、开发必备冷知识

6.1 count(*) VS count(1) 谁更快?

实测结果:在MySQL 8.0中,两者性能完全一致!优化器会自动处理。但是count(字段)会慢,因为要判断是否为NULL。

6.2 datetime和timestamp怎么选?

  • datetime:支持1000-9999年,物理存储8字节
  • timestamp:支持1970-2038年,自动转换时区,4字节
    建议:如果需要时区转换就用timestamp,否则用datetime

最后说两句

MySQL面试最可怕的地方在于——你以为会写CRUD就够了,其实每个问题都能挖出十八层地狱!建议小伙伴们:

  1. 亲手用EXPLAIN分析慢查询
  2. SHOW ENGINE INNODB STATUS看死锁日志
  3. 一定要自己搭主从环境体验复制延迟

记住,面试官最喜欢问的其实就三个方向:事务原理、索引优化、高可用方案。吃透这些核心点,MySQL面试直接横着走!(当然别忘了结合项目实际场景哦)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值