自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+

记录后端技术的深水区:MySQL、并发、JVM、分布式。原理为主,实战为辅,能少踩一个坑是一个。

后端工程师,专注把复杂的底层原理讲明白。主攻 MySQL / Java / 并发 / 分布式,坚持原创长文、图文并茂、拒绝浅尝辄止,持续更新中。

  • 博客(80)
  • 资源 (2)
  • 问答 (1)
  • 收藏
  • 关注

原创 AI应用 06 · 检索质量优化:混合检索、Rerank 与 Query 改写

本文探讨了纯向量检索在RAG系统中的局限,尤其在处理订单号、型号等精确匹配信息时表现不佳。提出通过混合检索——结合向量与关键词(如BM25)检索,利用RRF融合排名,再经Cross-Encoder重排序,显著提升召回准确率。同时引入Query改写与HyDE技术优化查询语义,使用户口语化问题更适配知识库文档风格。最终构建高效、精准的混合检索链路,实现从“能跑”到“好用”的跨越。

2026-09-21 14:44:20 290

原创 AI应用 05 · RAG 全链路:从一篇文档到一个可信答案

本文系统阐述RAG(检索增强生成)在商品知识库问答中的完整链路,分为索引期与查询期两大阶段。索引期完成文档预处理、语义分块、批量嵌入与向量存储;查询期则通过问题嵌入实现精准检索,结合上下文组装与生成控制,确保回答可信可引用。重点强调分块策略、重叠设计、元数据保留及增量更新等工程细节,揭示RAG效果优化需逐环节调优,而非简单“检索+生成”。

2026-09-21 14:27:11 478

原创 AI应用 04 · Embedding 与向量检索:语义相似是怎么算出来的

本文详解语义检索的核心——Embedding,解决关键词匹配无法处理同义改写、概念差异等问题。通过将文本转化为向量,利用余弦相似度衡量语义接近度,并结合HNSW等向量索引实现高效近似检索。文章还对比了pgvector、Milvus等向量数据库选型方案,以电商场景为例演示了基于pgvector的向量索引构建与查询流程,为RAG系统中的“检索”环节奠定基础。

2026-09-17 20:57:35 370

原创 AI应用 03 · Prompt 工程:让模型稳定输出你要的结构

本文系统阐述Prompt工程的工程化方法,聚焦如何让模型稳定输出结构化结果。通过Few-shot示例增强理解一致性,Chain-of-Thought提升推理透明度,结合JSON Schema与API级约束实现结构化输出,并引入防御机制应对Prompt注入攻击。最终强调Prompt需具备可测试性,如同代码般进行回归验证,确保在多版本、多场景下保持稳定可靠,为构建可信的AI应用提供可复用的工程范式。

2026-09-17 20:51:55 428

原创 AI应用 02 · LLM 基础:一次 API 调用背后发生了什么

本文以原生HTTP请求为例,深入解析大模型API的核心协议,涵盖Token、Context Window、角色结构与采样参数等关键概念。通过Java实现一次真实调用,揭示模型“看见”输入、“生成”输出的全过程,强调理解底层协议对排查问题、优化设计的重要性。文中指出:模型按Token处理文本,上下文窗口限制决定对话长度,角色分工影响输出行为,而temperature与top_p控制生成随机性。掌握这些基础,才能在实际应用中精准调控、高效构建AI系统。

2026-09-16 16:19:44 162

原创 AI应用 01 · 开篇:Java 后端工程师为什么要学 RAG 与 Agent

本文以客服退款场景切入,解析LLM应用开发中的核心概念:RAG(检索增强生成)解决“模型知道什么”,通过外部知识库提供准确依据;Agent(智能体)解决“模型能做什么”,赋予模型调用接口、执行任务的能力。二者并非二选一,而是协同构建可控、可信赖的AI应用系统。文章强调,后端工程师应聚焦于“应用层”——如何设计高效检索、可靠调用与容错机制,而非深入模型训练细节。全系列将以电商场景为背景,系统性拆解RAG与Agent的工程实现,助力开发者将大模型安全接入业务系统。

2026-09-16 16:16:52 382

原创 Redis 14 · 收官:生产调优与线上排障全景

Redis 线上问题很少只有一个原因:慢命令会拖长事件循环,内存上涨会触发淘汰,fork 会放大 COW,复制延迟又会影响故障转移。收官篇把前面所有机制串成一张排障地图。

2026-09-13 23:34:04 632

原创 Redis 13 · 分布式锁:从 SET NX 到 Redlock

本文系统阐述了基于Redis实现分布式锁的安全要点:需通过随机令牌确保锁释放安全,结合续期机制应对长任务,以fencing token防范进程暂停后旧请求误写。强调锁非唯一保障,关键操作须在数据库层校验版本或使用幂等性设计。主从复制下存在丢锁风险,Redlock虽提升容错但无法替代业务防护。最终提出生产实践清单,核心原则为“锁仅优化并发,正确性依赖业务层防御”。

2026-09-11 19:39:49 431

原创 Redis 12 · 缓存一致性:数据库与缓存双写怎么不乱

本文系统阐述了缓存与数据库一致性问题,强调“强一致”需明确定义时间窗口。核心原则为:先更新数据库,再删除缓存,避免并发读导致旧值回填。针对并发更新,提出延迟双删与版本号校验;通过消息驱动(如Outbox、binlog)实现可靠删除,确保幂等性;结合失败重试、兜底策略与对账验证,构建容错机制。关键在于以版本控制防止旧数据覆盖,用可观测性监控一致性状态,而非追求毫秒级同步。

2026-09-11 19:38:03 522

原创 Redis 11 · 缓存问题:穿透、击穿与雪崩

缓存难题在于失效、流量突增与回源压力叠加下的系统稳定性。穿透源于无效请求,需参数校验、空值缓存与布隆过滤器防御;击穿因热点Key过期引发并发回源,宜用互斥锁或逻辑过期;雪崩由大量Key同时失效或缓存层崩溃导致,需TTL随机抖动、分批预热与多级缓存。结合限流、降级、监控与演练,确保系统在异常下仍可服务。

2026-09-10 17:52:04 445

原创 Redis 10 · 集群:16384槽、扩缩容与请求路由

Redis Cluster 通过 16384 个槽位实现数据分片,基于 CRC16(key) mod 16384 路由。客户端需支持 MOVED(稳定重定向)与 ASK(临时重定向),并正确处理 Hash Tag 以保证多 Key 操作在同槽。集群使用 Gossip 协议实现故障检测与拓扑同步,扩容缩容通过迁槽完成,需控制迁移速度并避免热点集中。关键设计边界:跨槽事务不可行,热点需合理分片,迁移后应验证槽位归属与数据分布,确保服务稳定。

2026-09-10 17:48:55 281

原创 Redis 09 · 高可用:Sentinel 如何发现故障并完成切主

Sentinel 在 Redis 主从复制之上提供监控、通知与自动故障转移。它通过多个节点投票判定主观/客观下线,选举 Leader 并晋升新主,客户端需动态查询新地址。生产环境需合理设置超时并演练故障场景,重点优化客户端发现与连接池重建,避免误切主和双主写入。

2026-09-08 20:04:03 333

原创 Redis 08 · 主从复制:全量同步、增量同步与复制延迟

Redis主从复制通过复制流将主节点数据同步到副本,实现读扩展、故障接管与数据安全。复制默认异步,使用replication ID、offset和backlog定位同步进度;首次全量同步通过RDB快照+增量追平,断线后可根据backlog部分重同步,否则退化全量。文章还讨论了复制延迟、无盘复制、级联复制、WAIT及生产配置排障,强调复制不能替代持久化,也不等于自动高可用。

2026-09-08 19:58:34 452

原创 Redis 07 · 原子操作:事务、Pipeline、Lua 与 Functions

针对真实业务中“单命令原子 ≠ 业务流程原子”难题,文章区分了五种能力:Pipeline仅减少 RTT,不保证原子;MULTI/EXEC 提供连续执行但出错不回滚;WATCH 实现乐观锁,需重试;Lua 在服务端原子完成判断与修改;Functions 是Lua的可管理演进。核心在于根据并发条件校验、减少网络往返等四类问题选型,并关注错误处理、阻塞与Cluster限制。

2026-09-04 19:45:16 852 1

原创 Redis 06 · 内存管理:过期删除、淘汰策略与大 Key 治理

本文梳理Redis内存管理的三套机制:过期删除处理到期Key,内存淘汰在容量不足时牺牲有效Key,BigKey/HotKey与碎片治理控制结构性风险。文章从内存构成、TTL生命周期、主动/被动过期,到maxmemory策略选择、近似LRU/LFU,再到生产治理与排障,强调不能只背口诀,需结合实际配置和监控。

2026-09-04 19:39:47 510

原创 Redis 05 · 持久化:RDB 与 AOF 怎么保证数据不丢

Redis 持久化不可简化为“有 RDB/AOF 就不丢数据”。RDB 是时间点快照,有丢失窗口;AOF 记录增量写命令,但客户端收到 OK 不等于数据已落盘,关键在 write、fsync 与刷盘策略。文章从故障模型、RPO/RTO 出发,拆解 RDB 的 fork 与写时复制、AOF 的三种 appendfsync、AOF 重写及 Redis 7 多文件格式、混合持久化与恢复,并讨论性能抖动、容量规划和生产选型。

2026-09-03 22:16:35 509

原创 Redis 04 · 执行模型:一条命令的生命周期与 I/O 多路复用

以一条HGET命令的完整生命周期为例,梳理Redis从网络接入、I/O多路复用、RESP解析到命令校验执行、响应写回的全链路。明确Redis6 I/O线程只并行处理Socket读写与解析,核心命令仍在主线程串行执行;Pipeline减少RTT但非原子;慢命令、Lua脚本和阻塞操作会真正阻塞主线程,为生产延迟排障提供参考。

2026-09-03 22:10:35 347

原创 Redis 03 · 底层原理:RedisObject 与核心编码

Redis 逻辑类型与内部编码分层,通过 RedisObject 统一外壳实现解耦,编码会随元素数量、大小和版本变化。文章涵盖五种数据类型的底层 SDS、listpack、dict 等结构,并落脚于编码转换和生产影响,强调内存优化需结合数据规模。

2026-09-03 21:55:21 320

原创 Redis 02 · 数据结构:String 到 Stream 怎么选

选型核心是“先看访问模式,再选数据结构”:整体读写用String,字段局部更新用Hash,有序队列用List,去重与集合运算用Set,排行榜用Sorted Set,需消费确认用Stream。避免只背命令,应理解单次操作成本与生产边界。

2026-09-03 12:21:29 415

原创 Redis 01 · 开篇:Redis 为什么快

秒杀等热点流量下,Redis作为前置缓存,降低了数据库负载并吸收流量尖峰。其高性能源于五层设计:内存存储、适配数据结构的原生命令、串行执行避免锁竞争、I/O多路复用管理海量连接及短网络路径。

2026-09-03 11:40:22 452

原创 踩坑 - 压测三轮后 502:一个默认 10 的连接池如何拖垮整个服务

除了 Tomcat 那个"请求线程池",业务代码常自己开线程池做并行查询、异步任务。这些池子同样有core/max/queueCapacity/拒绝策略,配不好一样堆积。两个高频坑:① @Async不指定线程池时,早期默认走——它不复用线程、来一个建一个,高并发下疯狂创建线程直到 OOM;不传线程池时走,这是全 JVM 共享的池,被一个慢任务占满会连累所有用到它的地方。核心业务用独立、命名清晰的线程池做资源隔离,别共享、别吃默认。

2026-08-21 23:49:55 451

原创 并发 14 · 收官:虚拟线程与结构化并发

本文介绍了JDK 21虚拟线程的核心优势及使用方式。虚拟线程通过挂载/卸载机制,使同步阻塞代码也能实现高吞吐,解决了平台线程昂贵的问题。其轻量级特性允许创建数百万线程,不再需要复杂的线程池调参或异步回调改代码。文章从平台线程的成本切入,详细分析了虚拟线程的工作原理、创建方式(直接创建或使用ExecutorService)、使用注意事项(避免池化、pin问题),并介绍了配套的结构化并发和ScopedValue。最后对比了虚拟线程与传统线程池、响应式编程的适用场景,为Java并发编程提供了更简洁高效的解决方案。

2026-08-21 23:43:50 561 2

原创 并发 13 · 异步编排

摘要:本文探讨了异步编排在秒杀下单场景中的应用,分析了传统Future的局限性,并介绍了CompletableFuture如何通过链式调用解决任务依赖与并行问题。文章详细讲解了创建异步任务、串联任务(thenApply/thenCompose)、合并任务(thenCombine/allOf)以及异常处理等核心方法,强调使用独立线程池避免阻塞公共资源。最后结合秒杀案例,展示了如何构建高效、清晰的异步流水线,优化响应时间。全文提供代码示例和选型建议,帮助开发者实现高性能异步流程编排。

2026-08-20 21:35:15 436

原创 并发 12 · ThreadLocal

本文深入解析了ThreadLocal的核心机制与典型应用场景。ThreadLocal通过线程内部的Map存储数据,以ThreadLocal实例为key,实现线程隔离的数据存取。其弱引用设计虽避免ThreadLocal本身泄漏,却可能因value强引用导致内存滞留,需手动remove()释放。文章还探讨了父子线程间传递数据的InheritableThreadLocal,以及阿里开源的线程池场景解决方案TransmittableThreadLocal。最后强调生产环境中必须规范使用ThreadLocal,避免内

2026-08-20 21:29:12 711

原创 并发 11 · 同步工具类

摘要:秒杀系统预热等场景需要协调多线程节奏,JDK提供了同步工具类如CountDownLatch、CyclicBarrier等。CountDownLatch适用于一次性等待多个任务完成,通过计数器机制实现;CyclicBarrier可重复使用,用于多线程分批协作。两者的核心区别在于:CountDownLatch等待外部事件完成,CyclicBarrier等待协作线程到达汇合点。此外,Semaphore控制并发访问数量,Phaser支持多阶段协作,Exchanger实现线程间数据交换。这些工具解决了线程间的协

2026-08-20 00:03:04 616

原创 并发 10 · 阻塞队列与生产者-消费者

摘要: 秒杀系统的经典设计采用生产者-消费者模式,通过BlockingQueue实现请求缓冲。本文深入解析BlockingQueue的核心价值:1)相比手写wait/notify,它封装了线程安全的等待/唤醒机制;2)重点对比ArrayBlockingQueue(数组+单锁)与LinkedBlockingQueue(链表+双锁)的性能差异;3)介绍SynchronousQueue的直接传递特性及PriorityBlockingQueue等特殊队列。通过秒杀场景案例,演示BlockingQueue如何实现请求

2026-08-19 23:59:59 611

原创 并发 09 · 并发容器:ConcurrentHashMap

前两篇讲的是"锁"和"线程池",这一篇要讲一个几乎所有 Java 后端项目都在用、但很少有人真正搞懂内部构造的家伙——ConcurrentHashMap。本地缓存、计数器、限流器的滑动窗口,甚至线程池内部记录任务状态,背后经常都有它的身影。HashMap不是线程安全的,多线程并发put可能导致数据错乱,JDK 8 之前甚至会在扩容时因为链表操作顺序问题绕成一个环,get直接死循环、CPU 干到 100%;而老前辈Hashtable虽然安全,却是,无论put还是get。

2026-08-18 21:01:15 453

原创 并发 08 · 线程池原理与调优

本文深入探讨Java线程池的核心原理与工程实践,从基础概念到生产环境调优进行全面解析。主要内容包括: 线程池必要性:避免频繁创建销毁线程的开销,控制并发数量,提供统一调度入口 七大核心参数:详解corePoolSize、maximumPoolSize、keepAliveTime、workQueue等参数的作用与相互关系 任务执行流程:核心线程→队列→临时线程→拒绝的四步判断机制 队列选型陷阱:分析Executors工厂方法的潜在风险,特别是无界队列导致的内存溢出问题 拒绝策略选择:四种内置策略(Abort/

2026-08-18 20:58:57 392

原创 并发 07 · 死锁与线程安全策略

本文摘要: 并发编程中,死锁是最棘手的隐患之一——多个线程因互相持有对方所需资源而陷入永久等待。文章剖析了死锁的四大必要条件(互斥、持有并等待、不可剥夺、循环等待),并以转账场景为例演示死锁形成过程。通过 jstack 工具可快速定位死锁线程及其持有/等待的锁链。预防死锁的核心思路是破坏四大条件之一:推荐按固定顺序加锁(如账户ID排序)消除循环等待,或使用 ReentrantLock.tryLock 超时机制打破不可剥夺性。此外还区分了死锁与活锁(线程持续无效操作)、饥饿(资源长期被剥夺)的差异。

2026-08-17 20:24:26 488

原创 并发 06 · Lock 家族

本文深入探讨Java并发编程中的Lock家族,对比了synchronized与ReentrantLock的核心差异,分析了读写锁和StampedLock的适用场景。文章指出synchronized作为"傻瓜相机"简单可靠,而Lock家族则提供更精细的控制能力:ReentrantLock支持可中断、超时获取、公平锁及多条件;ReentrantReadWriteLock实现"读读共享"提升并发性能;JDK8的StampedLock通过乐观读进一步优化读多写少场景。最后强调选择锁的关键在于权衡功能需求与使用复杂度

2026-08-17 20:22:38 545

原创 并发 05 · AQS 原理

上一篇结尾我卖了个关子:、、、、线程池……半个 都建在同一个类身上,而这个类的骨架,就是"一个 的 state + 一个 CAS + 一个等待队列"。这个类,就是 AQS——(抽象队列同步器),Doug Lea 的封神之作,也是整个并发包的承重墙。为什么要专门花一篇啃它?因为 AQS 是那种"学一次,通一片"的知识点。你把它吃透了,后面第 6 篇的各种 、第 11 篇的各种同步工具,就都不用死记了——它们无非是在 AQS 这套骨架上,填不同的"业务逻辑"。反过来,如果不懂 AQS,那些类你只能一个个背

2026-08-16 21:24:03 385

原创 并发 04 · CAS 与原子类

摘要 CAS(Compare-And-Swap)是Java并发编程的核心技术,通过硬件指令实现无锁原子操作。其核心原理是“比较并交换”,仅当内存值等于预期值时更新为新值,否则重试。CAS避免了锁的开销,适用于低竞争场景,但存在ABA问题、自旋开销和单变量限制等缺陷。Java通过AtomicInteger等原子类实现无锁自增,并针对CAS的不足提供AtomicStampedReference(解决ABA)和LongAdder(优化高竞争性能)等方案。理解CAS是掌握Java并发容器(如ConcurrentHa

2026-08-16 21:21:58 268

原创 并发 03 · volatile 与 synchronized

上一篇我们在 JMM 那层把规则讲透了:happens-before、内存屏障、volatilefinal各自的承诺。这一篇,我们从抽象规则落到最常用的两个关键字本身,回答两个非常具体的问题:volatile。很多人对的印象还停留在"它是重量级锁、性能差、能用Lock就别用它"——这是一个过时了十几年的偏见。Java 6 之后,HotSpot 会尽量先采用较轻的获取路径,竞争加剧时才膨胀到重量级 monitor。

2026-08-15 11:22:59 297

原创 并发 02 · JMM 内存模型

如果这套规则因 CPU 而异、因 JVM 实现而异,那"一次编写、到处运行"的 Java 就成了一句空话——同一段并发代码,在 x86 上跑对了,换到 ARM 上就可能出诡异 bug。。它是整个 Java 并发大厦的——后面所有的volatileLock、原子类,本质上都是在 JMM 定下的规则里做文章。这也是为什么面试里问 JMM,问的从来不是"背几个名词",而是看你到底理不理解并发的底层契约。很多人对 JMM 的印象停留在"主内存、工作内存两块框",那只是最表层;这一篇要往下钻两层,把。

2026-08-15 11:19:31 479

原创 并发 01 · 开篇-并发为什么难

本文是Java并发编程系列的开篇,通过一个简单的多线程累加问题引出并发编程的核心挑战。文章指出并发难点的根源在于底层硬件机制(如CPU多核、缓存、编译器优化)导致的三大问题:原子性(如count++被拆分为多步操作)、可见性(线程修改的变量值对其他线程不可见)、有序性(代码执行顺序可能被重排)。通过分析进程与线程的区别、上下文切换的成本,解释了为何并发编程需要权衡性能与正确性。文章后续将围绕这些核心问题展开,系统讲解锁、volatile、线程状态管理等解决方案。全文以"理解机制而非记忆API"为导向,为后续

2026-08-13 21:38:41 851

原创 设计模式 23 · 收尾总纲:把二十三式串成一张地图

本文是「设计模式拆解」系列的收官之作,通过四个核心板块系统梳理了23种设计模式的应用与精髓。1. 模式在源码中的体现:列举JDK、Spring等框架中设计模式的实际应用(如单例、代理、观察者等),证明模式是优秀框架的通用语言;2. 易混淆模式辨析:总结9组高频易混模式(如工厂vs建造者、代理vs装饰器),强调区分关键在意图而非结构;3. 警惕过度设计:指出模式应针对真实变化而非想象需求,提倡YAGNI原则和渐进式重构;4. 全景知识地图:将23种模式与七大设计原则关联,揭示"组合优于继承""面向接口"等原则

2026-08-13 21:33:38 284

原创 设计模式 22 · 三个冷门模式:中介者、访问者、解释器

本文介绍了三种适用面较窄的设计模式——中介者、访问者和解释器。中介者模式用于协调多个对象的复杂交互,但容易导致"上帝类"问题;访问者模式适合在稳定数据结构上添加新操作,但对新增元素类型不友好;解释器模式用于解析自定义语法,但类爆炸且已有更优替代方案。这三种模式的共同点是适用场景有限且存在明显缺陷,作者强调了解它们的使用限制比掌握实现更重要,在实际开发中应谨慎使用,避免过度设计。文章通过具体代码示例说明了各模式的核心思想及适用边界,提倡以"何时不用"的角度看待设计模式。

2026-08-12 20:43:55 448

原创 设计模式 21 · 备忘录模式

备忘录模式(Memento)是一种在不破坏对象封装性的前提下,捕获并保存对象内部状态的设计模式,支持后续恢复到该状态。其核心在于由对象自身(原发器)创建备忘录来保存状态,备忘录对外封闭,仅原发器可读写。管理者(如草稿箱)仅负责存储备忘录而无法访问其内容。该模式通过权限控制(如内部类或包级私有)实现封装保护,适用于状态复杂、逆操作难以实现的场景(如订单草稿功能)。与命令模式(增量撤销)和原型模式(克隆对象)不同,备忘录模式通过全量快照实现状态恢复,常与其他模式配合使用。

2026-08-12 20:42:27 339

原创 设计模式 20 · 迭代器模式

迭代器模式是一种常用的设计模式,它提供统一的方式来遍历集合而不暴露其内部结构。Java 内置了该模式,通过 Iterable 和 Iterator 接口实现,使 for-each 循环能遍历所有集合。迭代器将遍历逻辑封装为独立对象,使集合内部结构的变化不影响使用方代码。此外,Java 的迭代器采用 fail-fast 机制,在遍历时检测集合修改并抛出异常,防止并发问题。该模式适用于需要统一遍历方式且隐藏内部实现的场景,如自定义集合类。

2026-08-11 21:09:27 374

原创 设计模式 19 · 命令模式

命令模式将操作封装成对象,实现请求与执行的解耦,支持撤销、排队等功能。核心在于通过"命令对象"记录操作细节,使请求可存储、传递和管理。典型应用包括订单操作撤销、线程池任务、事务处理等场景,提升系统灵活性与可扩展性。

2026-08-11 21:08:18 374

SwitchHosts_4.0.2.6057.dmg

switchhosts-4.0.2 Mac版,可以轻松配置hosts

2021-07-20

VLC播放器,支持DVD、音频 CD、VCD 及各类流媒体协议

VLC 是一款自由、开源的跨平台多媒体播放器及框架,可播放大多数多媒体文件,以及 DVD、音频 CD、VCD 及各类流媒体协议。 官网下载太慢,开源的

2019-01-22

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除