![](https://img-blog.csdnimg.cn/1edf9bef019f4ee2b8312f4fadcde5cc.jpeg?x-oss-process=image/resize,m_fixed,h_224,w_224)
JVM & 多线程
文章平均质量分 88
JVM & 多线程 详解
沙滩de流沙
不积跬步,无以至千里!
既然选择了远方,就要风雨兼程!
展开
-
【十五】不要问我JVM —— OOM及性能优化案例与解决
一、内存泄漏案例分析(一)public class Stack { private Object[] elements; private int size = 0; private static final int DEFAULT_INITIAL_CAPACITY = 16; public Stack() { elements = new Object[DEFAULT_INITIAL_CAPACITY]; } // 入栈 pu.原创 2021-07-31 21:50:47 · 581 阅读 · 0 评论 -
【十四】不要问我JVM !—— 性能调优工具
使用上述命令行工具或组合能帮您获取目标 Java 应用性能相关的基础信息,但它们存在下列局限:无法获取方法级别的分析数据,如方法间的调用关系、各方法的调用次数和调用时间等(这对定位应用性能瓶颈至关重要)。要求用户登录到目标 Java 应用所在的宿主机上,使用起来不是很方便。分析数据通过终端输出,结果展示不够直观。为此,JDK提供了一些内存泄漏的分析工具,如jconsole、jvisualvm等,用于辅助开发人员定位问题,但是这些工具很多时候并不足以满足快速定位的需求。所以这里我们介绍的工具相对多原创 2021-07-31 20:54:57 · 831 阅读 · 5 评论 -
【十三】不要问我JVM !—— 性能调优
一、背景说明1.1、生产环境中的问题生产环境发生内存溢出该如何处理?生产环境应该给服务器分配多少内存合适?如何对垃圾回收器的性能进行调优?生产环境CPU负载飙高该如何处理?生产环境应该给应用分配多少线程合适?不加log,如何确定请求是否执行了某一行代码?不加log,如何实时查看某个方法的入参与返回值?1.2、为什么要调优?防止出现OOM解决OOM减少Full GC出现的频率1.3、不同阶段的考虑上线前项目运行阶段线上出现OOM二、调优的概述2.1、监控.原创 2021-07-31 19:50:02 · 301 阅读 · 0 评论 -
【十二】不要问我JVM !—— 字节码
一、Java的前端编译器前端编译器的主要任务就是负责将符合Java语法规范的Java代码(. java)转换为符合JVM规范的字节码文件(.class)。javac是一种能够将Java源码编译为字节码的前端编译器。javac编译器在将Java源码编译为一个有效的字节码文件过程中经历了4个步骤分别是:词法解析语法解析语义解析生成字节码二、字节码2.1 字节码文件里是什么?源代码经过编译器编译之后便会生成一个字节码文件,字节码是一种二进制的类文件,它的内容是JVM的指令,而不像.原创 2021-07-31 18:15:51 · 471 阅读 · 1 评论 -
【十一】不要问我JVM !—— GC日志
通过阅读GC日志,我们可以了解Java虛拟机内存分配与回收策略。一、GC日志命令-XX:+PrintGC 输出GC日志(这个只会显示总的GC堆的变化)。类似: -verbose:gc-XX:+PrintGCDetails 输出GC的详细日志-XX:+PrintGCTimeStamps 输出GC的时间戳(以基准时间的形式)-XX:+PrintGCDateStamp 输出GC的时间戳(以日期的形式,如:2020-08-13T22:17:35.354+0800-XX:+PrintHeapAtGC原创 2021-07-31 13:11:12 · 156 阅读 · 0 评论 -
【十】不要问我JVM !—— 垃圾回收器
一、GC分类按垃圾回收器的线程数分分为串行并行垃圾回收器。串行垃圾回收器只有一个垃圾回收线程,并行垃圾回收器有多个垃圾回收线程。需要注意的是:串行以及并行垃圾回收器在回收垃圾的时候,都会Stop the World。(这里的线程指的是垃圾回收的线程)串行回收指的是在同一时间段内只允许有一个CPU用于执行垃圾回收操作,此时工作线程被暂停,直至垃圾收集工作结束。在诸如单CPU处理器或者较小的应用内存等硬件平台不是特别优越的场合,串行回收器的性能表现可以超过并行回收器和并发回收器。所以,串行.原创 2021-07-31 12:54:20 · 288 阅读 · 0 评论 -
【九】不要问我JVM !—— 引用
Reference 子类中只有终结器引用是包内可见的,其他3中引用类型均是public,可以在应用程序中直接使用。强引用(Strong Reference):最传统的“引用”的定义,是指在程序代码之中普遍存在的引用赋值,即类似“Object obj = new Object()”这种引用关系。无论任何情况下,只要强引用关系还存在,垃圾收集器就永远不会回收掉被引用的对象。软引用(Soft Reference):在系统将要发生内存溢出之前,将会把这些对象列入回收范围之中进行第二次回收。如果这次回收后还没有原创 2021-07-30 22:01:55 · 111 阅读 · 0 评论 -
【八】不要问我JVM !—— 垃圾!对不起我不是针对你,而是在座的各位!
一、什么是垃圾?垃圾是指在运行程序中没有任何指针指向的对象,这个对象就是需要被回收的垃圾。二、为什么需要GC?1.如果不进行垃圾回收,内存迟早都会被消耗完,因为不断地分配内存空间而不进行回收,就好像不停地生产生活垃圾而从来不打扫一样。2.除了释放没用的对象,垃圾回收也可以清除内存里的记录碎片。碎片整理将所占用的堆内存移到堆的一端,以便JVM将整理出的内存分配给新的对象。3.随着应用程序所应付的业务越来越庞大、复杂,用户越来越多,没有GC就不能保证应用程序的正常进行。而经常造成STW的GC又.原创 2021-07-30 18:14:03 · 197 阅读 · 0 评论 -
【七】不要问我JVM !—— 执行引擎 + 编译过程 + 解释器 + JIT编译器 + 热点代码探测
执行引擎是Java虚拟机的核心组成部分之一。虚拟机是一个相对于“物理机”的概念,这两种机器都有代码执行能力,其区别是物理机的执行引擎是直接建立在处理器、缓存、指令集和操作系统层面上的,而虚拟机的执行引擎则是由软件自行实现的,因此可以不受物理条件制约地定制指令集与执行引擎的结构体系,能够执行那些不被硬件直接支持的指令集格式。JVM的主要任务是负责装载字节码到其内部,但字节码并不能够直接运行在操作系统之上,因为字节码指令并非等价于本地机器指令,它内部包含的仅仅只是一些能够被JVM识别的字节码指令、符号表和.原创 2021-07-30 14:59:37 · 289 阅读 · 0 评论 -
【六】不要问我JVM !—— 对象实例化 + 内存布局 + 对象的访问定位 + 直接内存
一、对象的实例化字节码反编译后如下:1.1 创建对象的方式1. new:最常见的方式、Xxx 的静态方法,XxxBuilder/XxxFactory 的静态方法2. Class 的 newInstance 方法:反射的方式,只能调用空参的构造器,权限必须是 public3. Constructor 的 newInstance(XXX):反射的方式,可以调用空参、带参的构造器,权限没有要求4. 使用 clone():不调用任何的构造器,要求当前的类需要实现 Cloneable 接口,实.原创 2021-07-30 12:32:01 · 198 阅读 · 0 评论 -
【五】不要问我JVM !—— 方法区
一、栈、堆、方法区的交互关系 public class AppMain { //运行时,JVM把AppMain的信息都放入方法区 public static void main(String[] args) { //main成员方法本身放入方法区。 Sample test1 = new Sample( " 测试1 " );//test1是引用,所以放到栈区里,Sample是自定义对象应该放到堆里面 .原创 2021-07-30 11:36:28 · 158 阅读 · 0 评论 -
【四】不要问我JVM !—— 逃逸分析
一、堆是分配对象的唯一选择吗?在JVM中,对象是在Java堆中分配内存的,这是一个普遍的常识。但是,有一种特殊情况,那就是如果经过逃逸分析(Escape Analysis) 后发现,一个对象并没有逃逸出方法的话,那么就可能被优化成栈上分配。这样就无需在堆上分配内存,也无须进行垃圾回收了。这也是最常见的堆外存储技术。...原创 2021-07-29 22:14:30 · 230 阅读 · 0 评论 -
【三】不要问我JVM !—— 堆
一、堆(Heap)的核心概述一个进程就对应一个JVM实例,一个JVM实例就只有一个运行时数据区,只对应一个堆及一个方法区。原创 2021-07-28 23:26:05 · 301 阅读 · 1 评论 -
【二】不要问我JVM !—— 虚拟机栈 + 本地方法栈 + 本地方法接口
JVM定义了若干运行时数据区,其中一些随着JVM的启动而创建,退出而销毁。还有一些数据区域和线程一一对应,随着线程的开始而创建、结束而销毁。上图中,红色为线程共享区域(堆、元空间),灰色是线程私有(计数器、栈、本地栈)。一、JVM中的线程每个JVM只有一个RunTime实例,即运行时环境。JVM中,每个线程都和操作系统的线程一一对应,当一个Java线程准备执行时,此时操作系统本地线程也会对应创建。Java线程执行结束之后,操作系统本地线程也会回收。操作系统把所有线程安排到一个可用的CPU.原创 2021-07-26 22:53:53 · 287 阅读 · 0 评论 -
【一】不要问我JVM !
一、什么是JVM?JVM是Java的核心,因为所有的Java程序都运行在JVM上。那么什么是JVM?JVM即Java虚拟机,是一台执行Java字节码的虚拟机,拥有独立的运行机制(其运行的Java字节码也不一定由Java语言编译而成)。JVM就是二进制字节码的运行环境,负责装载字节码到其内部,解释、编译为对应的机器指令执行。要具有这种能力,就要做到每一条Java指令,JVM中都有详细的定义,如怎么取操作数、怎么定义变量等。JVM使得Java(也可以是其他语言)具有跨平台性、优秀的垃圾回收器以及可.原创 2021-07-25 18:53:59 · 209 阅读 · 0 评论 -
Java内存模型与线程
实现多线程我们知道可以继承Thread、实现Runnable接口等,但是为什么就实现呢?这篇文章就是解释多线程实现的底层原理。原创 2020-07-07 22:59:11 · 204 阅读 · 0 评论 -
常见 JVM垃圾回收器、内存分配策略、JVM调优
垃圾收集(Garbage Collection,下文简称GC),垃圾收集的历史远远比Java久远。经过半个世纪的发展,今天的内存动态分配与内存回收技术已经相当成熟,一切看起来都进入了“自动化”时代,那为什么我们还要去了解垃圾收集和内存分配?答案很简单:当需要排查各种内存溢出、内存泄漏问题时,当垃圾收集成为系统达到更高并发量的瓶颈时,我们就必须对这些“自动化”的技术实施必要的监控和调节。一、哪些内存需要回收?回答这个问题前需要先了解JVM到底有哪些内存区域,可参考:https://blog..原创 2020-07-05 22:47:19 · 390 阅读 · 0 评论 -
JVM运行时数据区域、内存溢出是怎样的?
一、Java内存区域Java虚拟机在执行Java程序的过程中会把它所管理的内存划分为若干个不同的数据区域。这些区域有各自的用途,以及创建和销毁的时间,有的区域随着虚拟机进程的启动而一直存在,有些区域则是依赖用户线程的启动和结束而建立和销毁。图1-1 运行时数据区1.1 程序计数器程序计数器是一块较小的内存,属于线程隔离区域,是当前线程所执行的字节码的行号指示器。字节码解释器工作时就是通过改变这个计数器的值来选取下一条需要执行的字节码指令,它是程序控制流的指示器,分...原创 2020-07-04 11:38:24 · 264 阅读 · 0 评论