返回当前 - 案例分析 - 分布式缓存与高并发
简单
案例题
2026年5月第5题

阅读以下关于 Redis 缓存与并发控制的叙述,在答题纸上回答问题1-3。
【说明】
某互联网平台在大促活动中提供优惠券领取和限量商品抢购功能。活动开始后的前几分钟,请求量会瞬间上升,大量用户同时访问库存、优惠券余量和订单创建接口。系统当前使用 Redis 缓存活动信息和库存数量,并通过数据库最终保存订单和扣减结果。在一次压测中,项目组发现热点商品库存被多个线程同时读取和扣减,偶尔出现重复领取、库存扣减不一致和数据库写入冲突等问题。
为解决高并发下共享资源竞争问题,张工建议采用悲观锁控制临界区,确保同一时刻只有一个请求能够修改关键资源;李工建议采用乐观锁,通过版本号或 CAS 方式减少阻塞,提高并发吞吐。架构师进一步提出,在 Redis 场景中可以结合分布式锁、原子递减、Lua 脚本、限流、队列削峰和异步落库等机制,综合保障库存、优惠券和订单数据的一致性。
项目组需要比较不同锁机制的适用场景,并给出 Redis 高并发控制的设计方案。

分值(8分

说明悲观锁的常见分类,并给出两类设计方案。

参考答案

悲观锁认为并发冲突较可能发生,因此访问共享资源前先加锁,其他请求必须等待或失败。
常见分类包括:共享锁和排他锁,读锁和写锁,数据库行锁和表锁,本地互斥锁和分布式锁。共享锁/读锁允许多个读请求并发访问,排他锁/写锁会独占资源,适用于库存扣减、优惠券领取等需要强约束的临界区。
两类设计方案可以这样写:第一,数据库悲观锁方案,利用行锁或 SELECT ... FOR UPDATE 锁定库存记录,在事务中完成校验和扣减;第二,Redis 分布式锁方案,使用 SET key value NX PX 获取锁,value 使用唯一请求标识,释放锁时通过 Lua 脚本校验 value 后删除,防止误删他人锁。还可以扩展读写锁方案,对读多写少资源区分读锁和写锁。

凯恩解析

本问考查悲观锁的概念、分类和工程化方案。悲观锁的基本假设是共享资源发生并发冲突的概率较高,因此在访问资源前先加锁,使同一时刻只有持锁请求能进入临界区。常见分类可以从多个角度写:按读写能力分为共享锁和排他锁,或读锁和写锁;按数据库粒度分为行锁、表锁和间隙锁;按部署范围分为本地互斥锁、数据库锁和分布式锁。共享锁适合多个读请求并发读取但不允许写,排他锁适合库存扣减、账户余额变更、优惠券领取这类必须独占修改的场景。
两类设计方案可以结合题干写。第一类是数据库悲观锁方案,使用事务和 SELECT ... FOR UPDATE 锁定库存行,在同一事务内完成查询余量、校验资格、扣减库存和写入订单。这种方案语义清楚、一致性强,但热点商品会造成数据库行锁竞争,吞吐量有限。第二类是 Redis 分布式锁方案,使用 SET key value NX PX 获取锁,其中 NX 保证不存在才设置,PX 设置过期时间防止死锁,value 使用唯一请求标识防止误删他人锁,释放锁时用 Lua 脚本先校验 value 再删除,保证判断和删除原子执行。如果业务耗时可能超过锁过期时间,还要考虑续期或缩短临界区。答题时把这些细节写出来,比只说“用 Redis 加锁”更符合架构师案例题要求。

还可以补充锁粒度和临界区设计。库存活动中不应把整个下单流程都放进锁里,否则支付、风控、远程调用都会拖长持锁时间,造成大量请求等待。更合理的做法是只锁定必须互斥的短操作,例如校验并扣减某个活动商品库存,后续订单创建、通知和落库尽量异步化。锁 key 也要有合适粒度,可以按活动ID和商品ID组织,而不是全站共用一把大锁。如果是 Redis 集群或主从切换场景,还需要理解单实例锁、RedLock 或基于数据库唯一约束的取舍,但考试中写清 SET NX PX、唯一 value、Lua 释放和超时控制通常已覆盖主要得分点。

联系我们
隐私协议
用户协议
微信公众号
知乎
小红书
浙ICP备2021029036号
@2022-2026
嘉兴市安芯网络科技有限公司 版权所有