Java高频面试考点场景题21

分布式转账面试题的核心,在于从三种方案中选择与场景匹配的技术路径。

分布式事务必要性:单机环境下@Transactional可通过同一数据库连接保证原子性,但分布式场景中跨库操作涉及多个连接,该注解无法生效,需引入分布式事务方案。

Seata AT 模式:阿里开源框架,通过添加@GlobalTransactional注解实现 0 侵入式开发,原理是记录undo log用于失败回滚,但存在全局锁导致性能较差,适用于并发量低的后台管理系统。

TCC 模式:分为try(冻结资源)、confirm(确认执行)、cancel(释放资源)三阶段,无全局锁且性能较好,但需手动编写三个接口,开发成本高,需配合数据库冻结字段使用。

本地消息表 + MQ:将跨库操作拆分为两个本地事务,通过消息队列串联,核心是扣款与写消息表在同一事务中保证原子性,定时任务投递消息,最终通过重试机制实现一致性,无全局锁且性能最优,是生产环境常用方案。

视频最后提出问题:本地消息表方案中,若 B 服务消费消息持续失败应如何处理。

仅回答 Seata 或 MQ 会触发阿里 P7 面试的死亡四连问,需掌握各分布式事务方案的深层问题及解决思路。

Seata AT 模式:零侵入但一阶段释放锁导致脏读,需 GlobalLock 配合 SELECT FOR UPDATE 解决;适合低并发后台业务。

TCC 模式:依赖 Try/Confirm/Cancel 三步业务逻辑,需改造表结构(如积分表加冻结字段);需解决空回滚(事务控制表校验 Try 记录)、悬挂(Try 前校验 Cancel 记录)、幂等性(全局事务 ID 拦截重复操作)三大坑,适合核心扣减场景。

Saga 模式:无需改表,通过补偿接口回滚,是第三方接口或老系统的无奈选择,但需保证幂等性。

方案选择维度:从一致性、性能、侵入性、表结构改造、适用场景五个维度决策,如核心扣减用 TCC、外部接口用 Saga、充值发货用 MQ。

分库分表按用户 ID 分片的设计,会导致非分片键查询触发全分片扫描,引发性能问题。

问题核心:订单系统按用户 ID 哈希分到 16 个库,客服通过订单号查询时,因订单号不是分片键,需扫描所有分片,导致 SQL 执行时间长达几十秒。

性能差异:用户查自己订单仅需几十毫秒,而客服查询因全分片扫描,性能差距显著。

解决方案:建立 "订单号→用户 ID" 映射表,客服先查映射表获取用户 ID,再走分片键查询;或使用 ElasticSearch 处理多维查询,避免直接访问分库分表。

考核重点:考察对分库分表设计中业务查询全局性的理解,而非仅掌握基础分片技术。

视频通过具体场景,展示了分库分表设计中分片键选择对不同查询场景的影响。

Redis 做消息队列丢数据的核心原因,在于 List 弹出即销毁、pubSub 发完即忘的机制缺陷,而 Stream 虽能规避但存在架构边界。

List 队列缺陷:采用 "拿到就删" 机制,消费者处理消息前(如扣减库存时)服务器崩溃,Redis 已删除消息导致数据丢失。

pubSub 模式问题:发完即忘不存储数据,消费者断网瞬间的消息会被直接丢弃。

Stream 机制优势:支持磁盘持久化,引入待处理列表备份消息,仅在业务执行完成并确认后销毁备份。

Stream 架构边界:作为内存数据库易因海量消息堆积撑爆内存,主从异步同步可能丢数据,无法实现业务与消息强一致性。

视频明确 Stream 适合发短信、记日志等轻量级异步通知,核心订单支付需用专业 MQ。

数据库主键选型的核心考察点是对 B + 树存储逻辑的理解,而非单纯记忆选项。

自增 ID 优势:以 "电影院排队" 类比,自增 ID 按顺序追加写入 B + 树,无页分裂,体积为八字节长整型,可优化非聚集索引的存储与查询效率。

UUID 缺陷:随机无序特性导致插入时需 "插队",引发页分裂和随机读,写入性能下降;字符长度超过 32 个,导致索引膨胀,内存缓存减少,查询效率降低。

雪花算法适配:分布式场景下,通过时间戳、机器号、流水号拼接生成 ID,既保证全局唯一,又因时间有序避免页分裂,解决分库分表主键冲突问题。

视频最后提出雪花算法是否存在坑的问题,引导观众在评论区讨论。

相关推荐
rOuN STAT2 小时前
Golang 构建学习
开发语言·学习·golang
番茄去哪了2 小时前
单体转微服务:正确的拆分思路与实战原则(上)
java·微服务·架构
AI进化营-智能译站2 小时前
ROS2 C++开发系列19-枚举定义机器人状态机|随机数生成仿真测试数据流
java·c++·ai·机器人
fengxin_rou2 小时前
黑马点评项目万字总结:从redis基础到实战应用详解
java·开发语言·分布式·后端·黑马点评
dEso RSET2 小时前
FrankenPHP实践
java
zhouwy1132 小时前
Golang 基础与实战笔记:从语法到微服务的全面指南
开发语言·go
灰子学技术2 小时前
Envoy TCP 层面的 Metric 指标分析
开发语言·网络·网络协议·tcp/ip·php
逸Y 仙X2 小时前
文章二十:Elasticsearch高亮搜索完全指南
java·大数据·运维·elasticsearch·搜索引擎·全文检索
清水白石0082 小时前
生成器不是性能银弹:什么时候该用 `yield` 省内存,什么时候它会拖慢 Python 数据处理吞吐?
开发语言·python·原型模式