图书目录

目    录

第1章 Java性能演变史:编程语言与虚拟机  1

1.1  Java生态系统的诞生  2

1.2  JDK的演进历程  2

1.3  Java HotSpot虚拟机及其编译策略  3

1.3.1  HotSpot执行引擎的演变  3

1.3.2  解释器和JIT编译  5

1.3.3  编译日志的打印  5

1.3.4  分层编译机制  6

1.3.5  客户端和服务器端编译器  7

1.3.6  分段代码缓存  7

1.3.7  自适应优化和反向优化  9

1.4  HotSpot内存管理单元:垃圾收集器  12

1.4.1  分代垃圾收集、STW算法和并发算法  13

1.4.2  新生代收集与弱分代假说  14

1.4.3  老年代收集和触发机制  15

1.4.4  并行和并发垃圾收集线程及其配置  16

1.5  Java语言及其生态系统的发展  18

1.5.1  Java 1.1至Java 1.4.2(J2SE 1.4.2)  18

1.5.2  Java 5 (J2SE 5.0)  19

1.5.3  Java 6 (Java SE 6)  22

1.5.4  Java 7 (Java SE 7)  24

1.5.5  Java 8 (Java SE 8)  28

1.5.6  Java 9(Java SE 9)至Java 16 (Java SE 16)  30

1.5.7  Java 17 (Java SE 17)  38

1.6  提升性能与拥抱变革  40

第2章 Java类型系统的发展及其性能影响  41

2.1  J2SE 5.0前的原始类型和字面量  42

2.2  J2SE 5.0前的引用类型  43

2.2.1  接口  43

2.2.2  类  45

2.2.3  数组  46

2.3  J2SE 5.0至Java SE 8类型系统的发展  47

2.3.1  枚举类型  47

2.3.2  注解  48

2.3.3  Java SE 8中其他重要改进  48

2.4  Java 9与Java 10类型系统的发展  50

2.5  Java 11至Java 17类型系统的发展  52

2.5.1  switch表达式  52

2.5.2  密封类  54

2.5.3  记录类型  55

2.6  Java 17之后:Valhalla项目  55

2.6.1  现有类型系统的性能影响  56

2.6.2  值类对内存管理的影响  61

2.6.3  重定义原始类型泛型支持  61

2.6.4  Valhalla项目  62

2.6.5  早期访问版本:先进的Valhalla理念  63

2.6.6  用例分析:理论与实际  64

2.6.7  不同语言间的对比  64

2.7  本章小结  65

第3章 从单体到模块化的演进之路  67

3.1  Java模块化系统概述  67

3.1.1  模块化系统介绍  68

3.1.2  模块化示例  68

3.1.3  编译和运行细节  70

3.1.4  新模块引入  70

3.2  从单体到模块化的JDK演变  75

3.3  JDK 11及更高版本中的模块化JDK  75

3.4  JDK 17模块化服务实现  75

3.4.1  服务提供者  76

3.4.2  服务消费者  77

3.4.3  示例  77

3.4.4  实现细节  78

3.5  JAR地狱和Jigsaw Layer  80

3.5.1  解决JAR地狱示例  81

3.5.2  实现细节  82

3.6  OSGi  87

3.6.1  OSGi概览  87

3.6.2  OSGi与Java模块层的相似之处  88

3.6.3  OSGi与Java模块层的差异  88

3.7  jdeps、jlink、jdeprscan和jmod简介  89

3.7.1  jdeps  89

3.7.2  jdeprscan  90

3.7.3  jmod  91

3.7.4  jlink  92

3.8  本章小结  93

3.8.1  性能影响  93

3.8.2  工具和未来展望  93

3.8.3  拥抱模块化编程范式  93

第4章 JVM统一日志接口  95

4.1  统一日志记录的必要性  95

4.2  统一日志与基础设施  96

4.3  统一日志系统中的标签  97

4.3.1  日志标签  97

4.3.2  标签指定  98

4.3.3  识别缺失信息  99

4.4  日志级别、输出和装饰器  99

4.4.1  日志级别  99

4.4.2  装饰器  101

4.4.3  日志输出  102

4.5  使用统一日志系统的示例  103

4.5.1  基准测试和性能测试  104

4.5.2  工具和技术  105

4.6  优化和管理统一日志系统  105

4.7  异步日志和统一日志系统  106

4.7.1  异步日志记录的优势  106

4.7.2  Java中异步日志实现  107

4.7.3  最佳实践和注意事项  108

4.8  JDK 11与JDK 17的日志增强功能  109

4.8.1  JDK 11  109

4.8.2  JDK 17  110

4.9  本章小结  110

第5章 端到端性能优化:JMH和微基准测试  111

5.1  本章简介  111

5.2  软件工程的核心支柱:性能工程  112

5.2.1  解码软件工程的各个层面  112

5.2.2  关键质量属性:性能  112

5.2.3  了解和评估性能  113

5.2.4  定义服务质量  113

5.2.5  衡量性能需求的成功标准  114

5.3  衡量Java应用程序性能的指标  114

5.3.1  占用空间  115

5.3.2  响应时间  118

5.3.3  吞吐量  119

5.3.4  可用性  119

5.3.5  响应时间与可用性  120

5.3.6  应用程序响应时间的时间轴分析  121

5.4  硬件对性能的影响  123

5.4.1  解码硬件与软件的动态关系  124

5.4.2  性能交响曲:编程语言、处理器和内存模型  125

5.4.3  性能提升之道:优化系统协作  126

5.4.4  内存模型:解读线程动态和性能影响  127

5.4.5  硬件上的并发  130

5.4.6  并发计算中的秩序机制:屏障、栅栏和volatile变量  132

5.4.7  深入理解原子性:Java内存模型和先行发生原则  133

5.4.8  多处理器系统中的并发内存访问和一致性  135

5.4.9  结合我在AMD、Sun Microsystems和ARM的经历深度挖掘NUMA  135

5.4.10  理论与实践的桥梁:并发、库和高级工具  139

5.5  一种灵活且全面的性能工程方法论  139

5.5.1  实验设计  139

5.5.2  自下而上的方法论  140

5.5.3  自上而下的方法论  142

5.5.4  制定工作说明书  142

5.5.5  一种自上而下的性能优化流程  143

5.5.6  以工作说明书为基础调查子系统  144

5.5.7  本节要点  150

5.6  性能基准的重要性  151

5.6.1  关键性能指标  151

5.6.2  从规划到分析建立性能基准制度  152

5.6.3  JVM内存管理基准测试综合指南  154

5.6.4  为何需要基准测试工具  156

5.6.5  Java微基准测试套件在性能优化中的作用  157

5.6.6  使用Maven入门Java微基准测试套件  158

5.6.7  在JMH中编写、构建和运行第一个微基准  158

5.6.8  基准测试阶段:预热和测量  160

5.6.9  循环优化和@Operations PerInvocation注解  161

5.6.10  JMH的基准模式  161

5.6.11  理解JMH中的分析器  162

5.6.12  JMH中的关键注解  162

5.6.13  使用JMH进行JVM基准测试  163

5.6.14  使用perfasm分析JMH基准  165

5.7  本章小结  166

第6章 OpenJDK中的高级内存管理和垃圾收集  167

6.1  本章简介  167

6.2  Java垃圾收集器概述  168

6.3  TLAB和PLAB  169

6.4  利用NUMA感知型的垃圾收集器优化内存访问  171

6.5  探索垃圾收集器的改进  173

6.5.1  通过G1垃圾收集器深入了解高级堆管理  174

6.5.2  区域化堆的优势  176

6.5.3  优化G1垃圾收集器参数实现峰值性能  178

6.5.4  适用于多TB堆内存的可扩展、低延迟的ZGC  186

6.6  垃圾收集器的未来趋势  198

6.7  评估垃圾收集器性能的实用技巧  200

6.8  评估不同工作负载下垃圾收集器的性能  202

6.8.1  事务工作负载类型  202

6.8.2  本节内容回顾  203

6.9  实时数据集压力  204

6.9.1  数据生命周期模式  204

6.9.2  对不同垃圾收集算法的影响  205

6.9.3  优化内存管理  205

第7章 运行时性能优化:聚焦字符串、锁及其他  207

7.1  本章简介  207

7.2  字符串优化  208

7.2.1  HotSpot虚拟机中的字面量和驻留字符串优化  209

7.2.2  字符串去重优化与G1垃圾收集器  211

7.2.3  减少字符串的内存占用  212

7.3  提升多线程性能:Java线程同步  223

7.3.1  监视器锁的作用  225

7.3.2  OpenJDK HotSpot虚拟机中的锁类型  225

7.3.3  代码示例和分析  226

7.3.4  Java锁机制的发展  228

7.3.5  自Java 9以来对竞争锁的优化  230

7.3.6  关于可视化竞争锁优化的性能工程实践  232

7.3.7  竞争锁优化的一些反思  242

7.3.8  一种间接锁改进:自旋等待提示  243

7.4  从Thread-Per-Task模型转向更具可扩展性的模型  245

7.4.1  传统的一对一线程映射  246

7.4.2  通过Thread-Per-Request模型提高可扩展性  246

7.4.3  虚拟线程重塑Java的并发编程  251

7.5  本章小结  256

第8章 使用OpenJDK HotSpot 虚拟机加速进入稳定状态  257

8.1  本章简介  257

8.2  优化JVM启动和预热的技术  258

8.3  Java应用程序从解码到稳定状态的时间  258

8.3.1  准备、就绪、启动  258

8.3.2  启动JVM的各个阶段  259

8.3.3  达到应用程序的稳定状态  260

8.3.4  应用程序的生命周期  261

8.4  启动和加速期间的状态管理  263

8.4.1  启动期间的状态  263

8.4.2  进入加速阶段和稳定状态  263

8.4.3  高效状态管理的优势  264

8.4.4  类数据共享  265

8.4.5  AOT编译  266

8.5  GraalVM彻底改变Java的稳态时间  272

8.6  新兴技术:用于检查点及恢复功能的CRIU和CRaC项目  274

8.7  优化无服务器环境和其他环境中的启动和加速阶段  277

8.7.1  无服务器计算和JVM优化  278

8.7.2  在容器化环境中确保快速启动和高效扩展  279

8.7.3  GraalVM的当今贡献  279

8.7.4  本节要点小结  279

8.8  利用OpenJDK HotSpot虚拟机提升预热性能  281

8.8.1  编译器的改进  281

8.8.2  分段代码缓存和Leyden项目的增强功能  284

8.8.3  从永久代到元空间向 峰值性能飞跃  284

8.9  本章小结  287

第9章 使用异构硬件打造JVM性能的未来  289

9.1  异构硬件和JVM简介  289

9.2  云计算中的异构硬件  291

9.2.1  硬件异构性  292

9.2.2  API兼容性和Hypervisor限制  292

9.2.3  性能权衡  293

9.2.4  资源竞争  293

9.2.5  云计算的特定限制  294

9.3  编程语言设计和工具链的作用  294

9.4  案例研究  296

9.4.1  LWJGL:一个基础示例  297

9.4.2  Aparapi:连接Java和OpenCL的桥梁  300

9.4.3  Sumatra项目:一项重大努力  303

9.4.4  TornadoVM:硬件加速器专用JVM  306

9.4.5  Panama项目:新视野  309

9.5  JVM与Panama项目  314

9.5.1  高级JVM语言API和本地库  315

9.5.2  Vector API和向量化数据处理系统  315

9.5.3  用于数据访问、缓存和格式化的加速器描述符  315

9.5.4  未来已来  316

9.6  结束语:畅想JVM性能工程  317