为什么需要并发编程
概述一句话并发编程是为了解决单线程处理不过来的问题——让程序能同时做多件事提升性能和响应速度。从一个真实场景说起想象一下你开了一家网店平时一天卖 100 单用一个客服处理订单绰绰有余。突然双十一来了同时涌入1000 个订单。如果你还坚持一个客服处理完一个再处理下一个会发生什么第一个用户等了 10 分钟才拿到确认第十个用户等了 100 分钟直接退款走人第一百个用户等到页面超时再也不来了问题的本质单线程单客服的处理能力是有限的当请求量超过处理速度时系统就会崩溃。解决方案多雇几个客服多线程同时处理多个订单。这就是并发编程的动机。 生活类比厨房做饭单线程一个人做饭想象你一个人在厨房做饭流程是这样的总耗时5 3 5 1 14 分钟。在这 14 分钟里你一直在忙但效率很低——洗菜时灶台是空的切菜时水龙头是空的。多线程厨房多人协作现在雇了三个人你负责切菜小王负责洗菜小李负责炒菜。三个人分工合作总耗时可能5 分钟就能上好几道菜。因为三个人同时在做不同的事。但是多人协作也会出问题假设你和小王都想用同一个锅你正在炒菜小王也想炒菜两个人抢一个锅结果菜洒了锅也坏了这就是并发编程中的资源争抢问题。解决方法是什么加锁——这个锅我在用你等一下。这就是后续章节要讲的synchronized和Lock。 单线程的 3 大瓶颈在现代计算机中单线程程序有三个致命问题瓶颈问题描述生活类比影响CPU 利用率低等待 I/O网络/磁盘/数据库时 CPU 空转厨师等外卖食材站在厨房发呆资源浪费处理速度慢响应性差一个任务卡住整个程序卡住厨师等食材所有客人都饿着用户体验差系统不可用吞吐量低无法利用多核 CPU厨房有 4 个灶台只用 1 个性能天花板低代码演示单线程的低效public class SingleThreadDemo { public static void main(String[] args) { long start System.currentTimeMillis(); // 模拟 3 个耗时任务每个 1 秒 task(任务1, 1000); task(任务2, 1000); task(任务3, 1000); long end System.currentTimeMillis(); System.out.println(总耗时: (end - start) ms); } static void task(String name, long sleepTime) { try { System.out.println(开始执行: name); Thread.sleep(sleepTime); // 模拟 I/O 等待 System.out.println(完成: name); } catch (InterruptedException e) { e.printStackTrace(); } } }预期输出开始执行: 任务1 完成: 任务1 开始执行: 任务2 完成: 任务2 开始执行: 任务3 完成: 任务3 总耗时: 3000ms问题3 个任务串行执行总耗时 任务1 任务2 任务3 3 秒。在等待任务1完成时CPU 是空闲的但没人用它。 并发解决了什么问题并发编程通过同时处理多个任务来解决单线程的瓶颈解决方案原理适用场景效果多核并行计算多个 CPU 核心同时执行不同任务CPU 密集型计算、加密性能提升 N 倍N核心数异步处理主线程不等待任务完成后回调I/O 密集型网络、数据库响应时间大幅降低资源利用等待时让出 CPU 给其他任务混合场景系统整体吞吐量提升代码演示多线程并行处理public class MultiThreadDemo { public static void main(String[] args) { long start System.currentTimeMillis(); // 创建 3 个线程同时执行 Thread t1 new Thread(() - task(任务1, 1000)); Thread t2 new Thread(() - task(任务2, 1000)); Thread t3 new Thread(() - task(任务3, 1000)); t1.start(); t2.start(); t3.start(); try { t1.join(); // 等待 t1 完成 t2.join(); // 等待 t2 完成 t3.join(); // 等待 t3 完成 } catch (InterruptedException e) { e.printStackTrace(); } long end System.currentTimeMillis(); System.out.println(总耗时: (end - start) ms); } static void task(String name, long sleepTime) { try { System.out.println(开始执行: name); Thread.sleep(sleepTime); System.out.println(完成: name); } catch (InterruptedException e) { e.printStackTrace(); } } }预期输出开始执行: 任务1 开始执行: 任务2 开始执行: 任务3 完成: 任务1 完成: 任务2 完成: 任务3 总耗时: 1000ms对比多线程总耗时1 秒是单线程的1/3。因为 3 个任务同时执行。 并发的演进Java 并发编程经历了 20 多年的演进版本新增特性解决的问题JDK 1.0Thread、synchronized基础多线程支持JDK 5.0java.util.concurrent包高效并发工具、线程池、并发集合JDK 8CompletableFuture、Lambda异步编程简化JDK 21虚拟线程、结构化并发轻量级线程、更好的并发控制 可跑代码3 个完整示例示例 1单线程处理慢public class SlowServer { public static void main(String[] args) { System.out.println( 单线程处理 3 个请求 ); long start System.currentTimeMillis(); // 模拟处理 3 个请求 handleRequest(用户A查询订单); handleRequest(用户B提交支付); handleRequest(用户C下载发票); long end System.currentTimeMillis(); System.out.println(总耗时: (end - start) ms); System.out.println(用户平均等待: (end - start) / 3 ms); } static void handleRequest(String request) { try { System.out.println(处理: request); Thread.sleep(1000); // 模拟网络 I/O System.out.println(完成: request); } catch (InterruptedException e) { e.printStackTrace(); } } }预期输出 单线程处理 3 个请求 处理: 用户A查询订单 完成: 用户A查询订单 处理: 用户B提交支付 完成: 用户B提交支付 处理: 用户C下载发票 完成: 用户C下载发票 总耗时: 3000ms 用户平均等待: 1000ms示例 2多线程并行处理快public class FastServer { public static void main(String[] args) { System.out.println( 多线程处理 3 个请求 ); long start System.currentTimeMillis(); // 创建 3 个线程并行处理 Thread t1 new Thread(() - handleRequest(用户A查询订单)); Thread t2 new Thread(() - handleRequest(用户B提交支付)); Thread t3 new Thread(() - handleRequest(用户C下载发票)); t1.start(); t2.start(); t3.start(); // 等待所有线程完成 try { t1.join(); t2.join(); t3.join(); } catch (InterruptedException e) { e.printStackTrace(); } long end System.currentTimeMillis(); System.out.println(总耗时: (end - start) ms); System.out.println(用户平均等待: (end - start) / 3 ms); } static void handleRequest(String request) { try { System.out.println(处理: request); Thread.sleep(1000); System.out.println(完成: request); } catch (InterruptedException e) { e.printStackTrace(); } } }预期输出 多线程处理 3 个请求 处理: 用户A查询订单 处理: 用户B提交支付 处理: 用户C下载发票 完成: 用户A查询订单 完成: 用户B提交支付 完成: 用户C下载发票 总耗时: 1000ms 用户平均等待: 333ms示例 3线程不安全的反例引出后续模块public class UnsafeCounter { private static int count 0; public static void main(String[] args) throws InterruptedException { System.out.println( 线程不安全示例 ); // 两个线程各加 10000 次 Thread t1 new Thread(() - { for (int i 0; i 10000; i) { count; // 这行不是原子操作 } }); Thread t2 new Thread(() - { for (int i 0; i 10000; i) { count; // 这行不是原子操作 } }); t1.start(); t2.start(); t1.join(); t2.join(); System.out.println(期望值: 20000); System.out.println(实际值: count); System.out.println(差值: (20000 - count)); // 为什么不是 20000 // 因为 count 不是原子操作多线程下会丢失更新 // 后续章节会详细讲解 CAS 和 synchronized } }预期输出每次运行可能不同 线程不安全示例 期望值: 20000 实际值: 15234 差值: 4766问题分析count看起来是一行代码但实际上分三步读取 count 的值加 1写回 count当两个线程同时执行时可能读到相同的值导致加 1 后覆盖对方的结果。这就是竞态条件。⚠️ 并发的代价预告多人协作虽然快但也会出问题问题描述生活类比后续章节竞态条件多个线程同时修改共享数据结果不可预期两个人同时改同一个文档02_原理与实现/04_锁体系总览死锁两个线程互相等待对方释放锁卡死两个人互相让路结果都卡在门口03_问题与应对/03_并发问题排查实战可见性问题一个线程修改了变量另一个线程看不到一个人在黑板上写字另一个人没看到02_原理与实现/03_并发内存模型线程安全多线程下数据结构可能损坏多人同时写账本账本可能乱套04_应用/07_并发集合详解怎么解决后面的篇目会一一拆解锁机制synchronized、ReentrantLock原子类AtomicInteger、CASvolatile 关键字并发集合ConcurrentHashMap线程池和同步器// 竞态条件示例两个人同时改同一个文档 public class RaceConditionExample { private static int balance 100; public static void main(String[] args) throws InterruptedException { // 模拟两个线程同时扣款 Thread t1 new Thread(() - { int temp balance; try { Thread.sleep(10); } catch (Exception e) {} balance temp - 50; System.out.println(用户A扣款后余额: balance); }); Thread t2 new Thread(() - { int temp balance; try { Thread.sleep(10); } catch (Exception e) {} balance temp - 50; System.out.println(用户B扣款后余额: balance); }); t1.start(); t2.start(); t1.join(); t2.join(); System.out.println(最终余额: balance); System.out.println(期望余额: 0, 实际: balance (应该为0)); } } 学习路径作为专栏入口这里告诉你接下来的模块怎么走学习阶段核心内容你会收获入门线程基础、内存模型、volatile、synchronized理解并发的基本概念能写简单的线程安全代码进阶锁机制、AQS、线程池、CompletableFuture看懂 JUC 源码会设计并发方案实战死锁排查、设计模式、虚拟线程能排查线上问题能设计并发架构 面试要点为什么用多线程提升性能多核 CPU 并行计算提升响应I/O 等待时 CPU 做其他事提升吞吐同时处理更多请求并发 vs 并行区别并发多个任务交替执行单核也能做到并行多个任务同时执行需要多核并发的代价竞态条件数据不一致死锁线程互相等待可见性修改不可见复杂度代码更难写、更难测单线程 vs 多线程性能对比CPU 密集型多线程 ≈ 单线程甚至更慢因为线程切换开销I/O 密集型多线程 单线程等待时做其他事如何避免线程安全问题加锁synchronized、ReentrantLock原子类AtomicInteger、CASvolatile保证可见性并发集合ConcurrentHashMap 总结要点记住这一句动机单线程处理不过来需要多线程并行类比一个人做饭 vs 厨房多人协作瓶颈CPU 空转、响应差、吞吐低解决多核并行、异步处理、资源复用代价竞态、死锁、可见性问题演进Thread → JUC → 虚拟线程下一步学线程基础理解线程是什么一句话总结并发编程是为了解决慢的问题但引入了乱的问题——后面的章节会教你如何又快又稳。

相关新闻

Unity新手入门实战:从零开发经典扫雷游戏,掌握数据驱动与MVC架构

Unity新手入门实战:从零开发经典扫雷游戏,掌握数据驱动与MVC架构

1. 项目概述:为什么从扫雷开始你的Unity之旅? 如果你刚接触Unity,面对一个空荡荡的3D场景和复杂的编辑器界面,可能会感到无从下手。网上教程要么是“Hello World”式的简单移动方块,要么是直接复刻复杂的3A大作&#x…

2026/7/21 22:48:38阅读更多 →
多维聚合后数据变形:窗口函数实战与跨维度计算

多维聚合后数据变形:窗口函数实战与跨维度计算

1. 这不是简单的“GROUP BY”——多维聚合中的数据变形术到底在解决什么问题?你有没有遇到过这样的场景:销售报表里要同时按“省份产品线季度”三个维度看销售额,但领导突然说:“再加一列,显示每个省份在各自大区里的销…

2026/7/21 23:55:22阅读更多 →
Graph-RAG实战:用知识图谱增强RAG提升技术文档问答准确率

Graph-RAG实战:用知识图谱增强RAG提升技术文档问答准确率

1. 项目概述:这不是一个“调用API”的玩具,而是一套可落地的知识中枢你有没有遇到过这样的场景:公司内部堆积了上百份PDF格式的行业白皮书、几十个Confluence页面的技术文档、还有散落在Slack频道里的关键决策记录——它们真实存在&#xff0…

2026/7/22 8:19:07阅读更多 →
AI 原生组织是什么 —— 人 + Agent 的超级协作如何落地

AI 原生组织是什么 —— 人 + Agent 的超级协作如何落地

AI 原生组织是什么 —— 人 Agent 的超级协作如何落地 引言:先回答一个问题,谁是数字员工 三年前谈企业 AI,大家还在问"大模型能做什么"。今天谈企业 AI,问题变了,变成"每个员工要不要带几个 Agent 工…

2026/7/22 15:28:42阅读更多 →
质控升级不用堆人力!AI报告审核神器IACheck,一键覆盖制造业检测报告全流程智能校验

质控升级不用堆人力!AI报告审核神器IACheck,一键覆盖制造业检测报告全流程智能校验

在制造业质控部门深耕多年的从业者,多半都有过被检测报告问题拖垮节奏的狼狈经历:生产线刚完成一批次新品试产,几十份原材料、半成品、成品的检测报告堆在质控岗的桌面上,审核员逐份核对数据,一会儿发现原材料的重金属…

2026/7/22 15:28:42阅读更多 →
ST178降本应用,电路,参数汇总集合

ST178降本应用,电路,参数汇总集合

单光束反射式红外光电传感器 正常集成性的反射式传感器价格普遍会贵一些,特别是进口可达几十上百一个,当你设备需要几十个这个传感器功能的时候就需要考虑价格问题,ST178相对解决了这个问题。 当你需要一个价格便宜的且集成的反射式传感器的时候可以选用ST178来去自己做一…

2026/7/22 15:28:42阅读更多 →
PICO4 VR多场景应用开发:从UI交互到真机部署全流程实战

PICO4 VR多场景应用开发:从UI交互到真机部署全流程实战

1. 项目概述:从UI到上机的PICO4 VR开发全链路 最近在折腾一个PICO4上的VR项目,核心需求是实现一个包含多个独立场景的应用,比如一个VR展厅,用户可以在主厅浏览,然后通过点击展品上的UI按钮,传送到对应的详细…

2026/7/22 15:28:42阅读更多 →
Kimi智能阅读网页的7大隐藏功能:从新手到专家的跃迁路径,现在掌握还不晚

Kimi智能阅读网页的7大隐藏功能:从新手到专家的跃迁路径,现在掌握还不晚

更多请点击: https://intelliparadigm.com 第一章:Kimi智能阅读网页的底层原理与能力边界 Kimi 智能阅读网页功能并非简单地抓取 HTML 文本,而是构建在多阶段语义理解流水线上:首先通过 Chromium 渲染引擎执行 JavaScript 并生成…

2026/7/22 15:28:42阅读更多 →
35岁程序员焦虑?别慌!这5条路让你不再迷茫,轻松转型!

35岁程序员焦虑?别慌!这5条路让你不再迷茫,轻松转型!

昨晚十一点多,一个老同事给我发微信。 他说公司又裁了一批人,自己虽然留下来了,但心里发慌。干了十二年开发,每天盯着电脑,突然想不明白一件事: “如果哪天不写代码了,我还能干什么?…

2026/7/22 15:26:40阅读更多 →
Go语言静态资源打包方案对比与实践指南

Go语言静态资源打包方案对比与实践指南

1. 项目背景与核心需求在Go语言开发中,我们经常需要处理静态资源文件的打包问题。无论是Web应用的模板文件、前端资源,还是配置文件、证书等,都需要随程序一起分发。传统做法是将这些文件与编译后的二进制文件放在同一目录下,但这…

2026/7/22 0:53:59阅读更多 →
Go语言实现高性能LDAP认证服务的架构与实践

Go语言实现高性能LDAP认证服务的架构与实践

1. 项目背景与核心价值LDAP(轻量级目录访问协议)作为企业级身份认证的黄金标准,已经服务了超过80%的财富500强公司。我在金融科技领域实施统一认证体系时,发现传统Java方案存在启动慢、内存占用高等痛点。而Go语言凭借其协程并发模…

2026/7/22 0:53:59阅读更多 →
【AI面试官实战指南】:用ChatGPT模拟10类高频技术岗面试,3天提升应答精准度92%

【AI面试官实战指南】:用ChatGPT模拟10类高频技术岗面试,3天提升应答精准度92%

更多请点击: https://intelliparadigm.com 第一章:AI面试官实战指南的核心价值与适用场景 AI面试官并非替代人类HR的“黑箱工具”,而是以可解释、可审计、可迭代的方式,赋能招聘全链路的关键基础设施。其核心价值在于将主观经验沉…

2026/7/22 0:53:59阅读更多 →
中小企业小程序开发公司怎么选:预算、上手和售后避坑指南

中小企业小程序开发公司怎么选:预算、上手和售后避坑指南

中小企业做小程序,最常见的矛盾是预算有限,但又不希望功能太单薄;没有技术团队,但又希望后续能自己运营;想快速上线,又担心隐性收费和售后失联。选型时如果只看“低价套餐”或“案例数量”,很容…

2026/7/22 0:01:17阅读更多 →
GEO优化如何沉淀长期内容资产?广拓时代谈AI搜索时代的内容ROI

GEO优化如何沉淀长期内容资产?广拓时代谈AI搜索时代的内容ROI

企业做营销,最怕钱花完了,资产没有留下。 效果广告能带来一段时间的曝光,但预算停止后,流量往往也随之停止。短视频内容可能在几天内冲高,也可能很快沉下去。AI搜索时代,企业需要重新思考一个问题&#xff…

2026/7/22 0:01:17阅读更多 →
Agent 终态判定:何时该停止思考、给出最终回复

Agent 终态判定:何时该停止思考、给出最终回复

Agent 终态判定:何时该停止思考、给出最终回复 一、你的 Agent 在"再想想"的循环里绕了 12 轮,用户已经关窗口了 Agent 与人最大的区别是:人知道什么时候该停下来给答案,Agent 会一直"想"下去。你给 Agent 接…

2026/7/22 0:01:17阅读更多 →
YOLOv8推理性能优化:从1.2FPS到35FPS的全链路加速实践

YOLOv8推理性能优化:从1.2FPS到35FPS的全链路加速实践

如果你在部署 YOLOv8 时,发现推理速度只有可怜的 1-2 FPS,而别人的演示视频却能跑到 30 FPS 以上,那么问题很可能不在模型本身,而在于你的整个处理链路。很多开发者拿到一个训练好的 YOLOv8 模型后,会直接使用官方示例…

2026/7/21 22:53:50阅读更多 →
Coze与Dify对比指南:低代码AI应用开发从入门到实战

Coze与Dify对比指南:低代码AI应用开发从入门到实战

1. 从零到一:为什么你需要了解 Coze 和 Dify?如果你对 AI 应用开发感兴趣,但一看到“大模型”、“智能体”、“工作流”这些词就头疼,觉得门槛太高,那这篇文章就是为你准备的。很多开发者,包括我自己&#…

2026/7/21 18:53:30阅读更多 →
AI生图工具怎么选?2026年6月版实测对比

AI生图工具怎么选?2026年6月版实测对比

做自媒体的朋友应该都有体会:配图一直是个让人头疼的问题。2026年,AI生图工具已经非常成熟了,但工具太多反而不知道怎么选。以下是截至2026年6月我对主流AI生图工具的实测对比。Midjourney V8.1:速度之王2026年6月11日&#xff0c…

2026/7/21 18:53:30阅读更多 →