《JVM由浅入深学习【五】 2024-01-08》JVM由简入深学习提升分享
目录
- JVM何时会发生堆内存溢出?
- 1. 堆内存溢出的定义
- 2. 内存泄漏的原因
- 3. 堆内存溢出的常见场景
- 4. JVM参数调优
- 5. 实际案例分析
- JVM如何判断对象可以回收
- 1.可达性分析的基本思路
- 2.实际案例
- 3.可以被回收的对象
- 4.拓展, 谈谈 Java 中不同的引用类型?
- 结语
- 感谢阅读
JVM何时会发生堆内存溢出?
前言:
欢迎来到本篇博客,我们将深入探讨 Java 虚拟机(JVM)中堆内存溢出的情况。理解这些情况对于避免内存问题和编写稳定的Java应用程序至关重要。
1. 堆内存溢出的定义
在Java中,堆内存溢出指的是当应用程序在堆内存中创建的对象无法被垃圾回收器有效回收,导致堆内存不足。这是一种常见的内存问题,经常会导致程序的崩溃。
2. 内存泄漏的原因
-
无效的引用: 对象的引用没有及时释放,导致垃圾回收器无法回收不再使用的对象。
-
循环引用: 对象之间存在相互引用,形成了循环链,使得这些对象都无法被垃圾回收。
3. 堆内存溢出的常见场景
-
大对象导致的溢出: 当创建大量大对象(如大数组)时,堆内存可能不足。
-
长时间运行的应用: 在长时间运行的Java应用程序中,由于对象的持续创建和保留,可能导致堆内存溢出。
4. JVM参数调优
-
堆内存大小设置: 可通过
-Xms
和-Xmx
参数设置堆内存的初始大小和最大大小,合理调整可以减少溢出的风险。java -Xms256m -Xmx512m -jar your-application.jar
5. 实际案例分析
考虑以下代码片段,它在一个循环中创建大量对象,但却没有释放引用:
import java.util.ArrayList;
import java.util.List;public class HeapMemoryOverflowExample {public static void main(String[] args) {List<String> stringList = new ArrayList<>();try {while (true) {// 创建大量字符串对象String largeString = new String(new char[1000000]);// 将字符串对象添加到集合中stringList.add(largeString);}} catch (OutOfMemoryError e) {System.out.println("堆内存溢出异常捕获:" + e.getMessage());}}
}
在这个例子中,由于对象持续被添加到stringList
列表中,垃圾回收器无法回收这些对象,最终导致堆内存溢出。
JVM如何判断对象可以回收
Java虚拟机(JVM)通过垃圾回收机制来自动管理内存,判断哪些对象可以被回收是垃圾回收的核心问题。JVM使用一种称为"可达性分析"的方法来判断对象的可达性,即判断对象是否还与引用链中的任何强引用相连。如果一个对象不再与任何强引用相连,那么它就成为不可达对象,可以被垃圾回收。
1.可达性分析的基本思路
-
根搜索算法(GC Roots): 通过一系列称为GC Roots的根对象作为起始点,从这些根对象开始向下搜索,能够到达的对象称为可达对象,不能到达的对象即为不可达对象。
-
GC Roots的类型:
- 虚拟机栈中引用的对象: 在方法的局部变量表中引用的对象。
- 本地方法栈中JNI(Java Native Interface)引用的对象: JNI是Java调用本地语言的接口,本地方法中引用的Java对象。
- 方法区中类静态属性引用的对象: 静态属性属于类的,它引用的对象也属于可达对象。
- 方法区中常量引用的对象: 常量池中的字符串常量等。
2.实际案例
考虑以下代码,演示了一个对象何时成为不可达对象:
public class GarbageCollectionExample {public static void main(String[] args) {Object obj1 = new Object(); // 强引用 obj1 指向新创建的对象Object obj2 = new Object(); // 强引用 obj2 指向新创建的对象obj1 = null; // obj1 不再指向对象,成为不可达对象System.gc(); // 提醒垃圾回收器进行垃圾回收// 在这里,垃圾回收器可能会回收 obj1 所指向的对象}
}
在上述代码中,obj1
一开始指向一个新创建的对象,后来被置为null
,不再与任何强引用相连。当程序调用System.gc()
提醒垃圾回收器进行垃圾回收时,垃圾回收器可能会回收obj1
原来所指向的对象。
要注意的是,垃圾回收器的执行是不确定的,调用System.gc()
并不一定会立即触发垃圾回收。这只是一个提示,实际回收时机由垃圾回收器自行决定。
3.可以被回收的对象
1、在虚拟机栈(栈中的本地变量表)中引用的对象,警如各个线程被调用的方法堆栈中使用到的参数、局部变量、临时变量等所引用的对象;
2、方法区/元空间中的类静态属性引用的对象
3、方法区/元空间中的常量引用的对象
4、在本地方法栈中JNI (即通常所说的 Native 方法) 引用的对象
5、Java 虚拟机内部的引用,如基本数据类型对应的 Class 对象,一些常驻的异常对象 (比如
NullPointExcepiton、OutOfMemoryError) 等,还有系统类加载器
6、所有被同步锁 (synchronized 关键字) 持有的对象;
7、反映 Java 虚拟机内部情况的JMXBean、JVMTI 中注册的回调本地代码缓存等
4.拓展, 谈谈 Java 中不同的引用类型?
Java 里有不同的引用类型,分别是强引用、软引用、弱引用 和 虚引用
强引用: Object object = new Object() ;
软引用: SoftReference 内存充足时不回收,内存不足时则回收;
弱引用: WeakReference 不管内存是否充足,只要 GC 一运行就会回收该引用对象
虚引用: PhantomReference 这个其实暂时忽略也行,因为很少用,它形同虚设,就像没有引用一样,其作用就是该引用对象被 GC 回收时候触发一个系统通知,或者触发进一步的处理
结语
在Java中,垃圾回收机制是一项重要的特性,它通过判断对象的可达性来自动管理内存,确保程序运行时不会因为内存泄漏而导致性能问题。了解对象何时成为不可达对象,以及垃圾回收的基本原理,对于编写高效的Java程序至关重要。
通过本文的介绍,我们深入了解了JVM如何判断对象是否可以回收,以及可达性分析的基本思路。在编写Java程序时,及时释放不再需要的对象引用是一种良好的编程习惯,有助于提高程序的性能和资源利用率。
感谢阅读
感谢您阅读本篇关于JVM的文章。希望通过这篇分享,您对Java内存管理和垃圾回收有了更深入的理解。如果有任何问题或建议,欢迎在评论区与我们分享。愿您的编程之路愉快!
相关文章:
《JVM由浅入深学习【五】 2024-01-08》JVM由简入深学习提升分享
目录 JVM何时会发生堆内存溢出?1. 堆内存溢出的定义2. 内存泄漏的原因3. 堆内存溢出的常见场景4. JVM参数调优5. 实际案例分析 JVM如何判断对象可以回收1.可达性分析的基本思路2.实际案例3.可以被回收的对象4.拓展, 谈谈 Java 中不同的引用类型? 结语感…...

FastDFS之快速入门、上手
知识概念 分布式文件系统 通过计算机网络将各个物理存储资源连接起来。通过分布式文件系统,将网络上任意资源以逻辑上的树形结构展现,让用户访问网络上的共享文件更见简便。 文件存储的变迁: 直连存储:直接连接与存储…...

Vue 中的 ref 与 reactive:让你的应用更具响应性(中)
🤍 前端开发工程师(主业)、技术博主(副业)、已过CET6 🍨 阿珊和她的猫_CSDN个人主页 🕠 牛客高级专题作者、在牛客打造高质量专栏《前端面试必备》 🍚 蓝桥云课签约作者、已在蓝桥云…...

【数据库基础】Mysql与Redis的区别
看到一篇不错的关于“Mysql与Redis的区别”的文章,转过来记录下~ 文章目录 一、数据库类型二、运行机制三、什么是缓存数据库呢?四、优缺点比较五、区别总结六、数据可以全部直接用Redis储存吗?参考资料 一、数据库类型 Redis:NOS…...

JVM工作原理与实战(六):类的生命周期-连接阶段
专栏导航 JVM工作原理与实战 RabbitMQ入门指南 从零开始了解大数据 目录 专栏导航 前言 一、类的生命周期 1.加载(Loading) 2.连接(Linking) 3.初始化(Initialization) 4.使用(Using&…...
【OCR】 - Tesseract OCR在Windows系统中安装
Tesseract OCR 在Windows环境下安装Tesseract OCR(Optical Character Recognition)通常包括以下几个步骤: 下载Tesseract 访问Tesseract的GitHub发布页面:https://github.com/tesseract-ocr/tesseract/releases找到适合你操作系…...

YOLOv8改进 | 损失函数篇 | SlideLoss、FocalLoss分类损失函数助力细节涨点(全网最全)
一、本文介绍 本文给大家带来的是分类损失 SlideLoss、VFLoss、FocalLoss损失函数,我们之前看那的那些IoU都是边界框回归损失,和本文的修改内容并不冲突,所以大家可以知道损失函数分为两种一种是分类损失另一种是边界框回归损失,上一篇文章里面我们总结了过去百分之九十的…...
计算机网络试题——填空题(附答案)
在OSI模型中,第一层是____________层。 答案:物理(Physical) TCP协议是一种_____________连接的协议。 答案:面向连接(Connection-oriented) IPv6地址的位数是____________。 答案:1…...

第二证券:股票私募仓位指数创近八周新高
1月8日,A股几大首要指数全线收跌,上证指数收于日内最低点2887.54点,间隔上一年5月份的阶段高点3418.95点现已跌去了15.54%。 不过,虽然商场仍未清晰止跌,私募基金们却现已进场“抄底”。私募排排网最新发布的私募仓位…...
35-javascript基础,引入方式;变量命名规范
html分为三部分;结构html,表现css,行为js;js就是javascript js包含三部分: ECMAScript:简称ES,ES5,ES6核心语法 DOM:获取和操作html元素的标准方法;BOM&am…...

笔试案例2
文章目录 1、笔试案例22、思维导图 1、笔试案例2 09)查询学过「张三」老师授课的同学的信息 selects.*,c.cname,t.tname,sc.score from t_mysql_teacher t, t_mysql_course c, t_mysql_student s, t_mysql_score sc where t.tidc.cid and c.cidsc.cid and sc.sids…...
【嵌入式-网络编程】vmware中使用UDP广播失败问题
问题描述: 自己在vmware中搭建了2台虚拟机,虚拟机A向虚拟机A和虚拟机B发送广播信息,接收端在虚拟机A和虚拟机B,这个时候,由于没配置sin.sin_addr.s_addr htonl(INADDR_ANY);,而是配置的inet_pton(AF_INET,…...

2020年认证杯SPSSPRO杯数学建模D题(第二阶段)让电脑桌面飞起来全过程文档及程序
2020年认证杯SPSSPRO杯数学建模 D题 让电脑桌面飞起来 原题再现: 对于一些必须每天使用电脑工作的白领来说,电脑桌面有着非常特殊的意义,通常一些频繁使用或者比较重要的图标会一直保留在桌面上,但是随着时间的推移,…...

vue3 修饰符大全(近万字长文)
系列文章目录 TypeScript 从入门到进阶专栏 文章目录 系列文章目录前言一、事件修饰符(Event Modifiers)1、.stop(阻止事件冒泡)2、.prevent(阻止事件的默认行为)3、.capture(使用事件捕获模式…...

HarmonyOS@State装饰器:组件内状态
State装饰器:组件内状态 State装饰的变量,或称为状态变量,一旦变量拥有了状态属性,就和自定义组件的渲染绑定起来。当状态改变时,UI会发生对应的渲染改变。 在状态变量相关装饰器中,State是最基础的&…...

如何让GPT支持中文
上一篇已经讲解了如何构建自己的私人GPT,这一篇主要讲如何让GPT支持中文。 privateGPT 本地部署目前只支持基于llama.cpp 的 gguf格式模型,GGUF 是 llama.cpp 团队于 2023 年 8 月 21 日推出的一种新格式。它是 GGML 的替代品,llama.cpp 不再…...

使用开源通义千问模型(Qwen)搭建自己的大模型服务
目标 1、使用开源的大模型服务搭建属于自己的模型服务; 2、调优自己的大模型; 选型 采用通义千问模型,https://github.com/QwenLM/Qwen 步骤 1、下载模型文件 开源模型库:https://www.modelscope.cn/models mkdir -p /data/…...
Java工程师面试题解析与深度探讨
Java工程师面试题解析与深度探讨 第一部分:引言 Java作为一门广泛应用的编程语言,拥有庞大的生态系统,Java工程师因此成为众多企业追逐的目标。而在Java工程师的招聘中,面试是了解候选人技能和经验的核心环节。本文将深入探讨一…...

Linux下安装JET2
0. 说明: JET2是一个基于Joint Evolutionary Trees的利用序列和结构信息预测蛋白质界面的软件,详情见: http://www.lcqb.upmc.fr/JET2/JET2.html,http://www.lgm.upmc.fr/JET/JET.html 和 https://doi.org/10.1371/journal.pcbi.1004580 本…...
【PostgreSQL】表管理-表继承
PostgreSQL 表继承 PostgreSQL 实现了表继承,这对于数据库设计人员来说是一个有用的工具。(SQL:1999 及更高版本定义了类型继承功能,该功能在许多方面与此处描述的功能不同。 让我们从一个例子开始:假设我们正在尝试…...
基于服务器使用 apt 安装、配置 Nginx
🧾 一、查看可安装的 Nginx 版本 首先,你可以运行以下命令查看可用版本: apt-cache madison nginx-core输出示例: nginx-core | 1.18.0-6ubuntu14.6 | http://archive.ubuntu.com/ubuntu focal-updates/main amd64 Packages ng…...

理解 MCP 工作流:使用 Ollama 和 LangChain 构建本地 MCP 客户端
🌟 什么是 MCP? 模型控制协议 (MCP) 是一种创新的协议,旨在无缝连接 AI 模型与应用程序。 MCP 是一个开源协议,它标准化了我们的 LLM 应用程序连接所需工具和数据源并与之协作的方式。 可以把它想象成你的 AI 模型 和想要使用它…...

ESP32读取DHT11温湿度数据
芯片:ESP32 环境:Arduino 一、安装DHT11传感器库 红框的库,别安装错了 二、代码 注意,DATA口要连接在D15上 #include "DHT.h" // 包含DHT库#define DHTPIN 15 // 定义DHT11数据引脚连接到ESP32的GPIO15 #define D…...

屋顶变身“发电站” ,中天合创屋面分布式光伏发电项目顺利并网!
5月28日,中天合创屋面分布式光伏发电项目顺利并网发电,该项目位于内蒙古自治区鄂尔多斯市乌审旗,项目利用中天合创聚乙烯、聚丙烯仓库屋面作为场地建设光伏电站,总装机容量为9.96MWp。 项目投运后,每年可节约标煤3670…...
如何为服务器生成TLS证书
TLS(Transport Layer Security)证书是确保网络通信安全的重要手段,它通过加密技术保护传输的数据不被窃听和篡改。在服务器上配置TLS证书,可以使用户通过HTTPS协议安全地访问您的网站。本文将详细介绍如何在服务器上生成一个TLS证…...

三分算法与DeepSeek辅助证明是单峰函数
前置 单峰函数有唯一的最大值,最大值左侧的数值严格单调递增,最大值右侧的数值严格单调递减。 单谷函数有唯一的最小值,最小值左侧的数值严格单调递减,最小值右侧的数值严格单调递增。 三分的本质 三分和二分一样都是通过不断缩…...

Golang——7、包与接口详解
包与接口详解 1、Golang包详解1.1、Golang中包的定义和介绍1.2、Golang包管理工具go mod1.3、Golang中自定义包1.4、Golang中使用第三包1.5、init函数 2、接口详解2.1、接口的定义2.2、空接口2.3、类型断言2.4、结构体值接收者和指针接收者实现接口的区别2.5、一个结构体实现多…...
SQL Server 触发器调用存储过程实现发送 HTTP 请求
文章目录 需求分析解决第 1 步:前置条件,启用 OLE 自动化方式 1:使用 SQL 实现启用 OLE 自动化方式 2:Sql Server 2005启动OLE自动化方式 3:Sql Server 2008启动OLE自动化第 2 步:创建存储过程第 3 步:创建触发器扩展 - 如何调试?第 1 步:登录 SQL Server 2008第 2 步…...
Java 与 MySQL 性能优化:MySQL 慢 SQL 诊断与分析方法详解
文章目录 一、开启慢查询日志,定位耗时SQL1.1 查看慢查询日志是否开启1.2 临时开启慢查询日志1.3 永久开启慢查询日志1.4 分析慢查询日志 二、使用EXPLAIN分析SQL执行计划2.1 EXPLAIN的基本使用2.2 EXPLAIN分析案例2.3 根据EXPLAIN结果优化SQL 三、使用SHOW PROFILE…...

CSS3相关知识点
CSS3相关知识点 CSS3私有前缀私有前缀私有前缀存在的意义常见浏览器的私有前缀 CSS3基本语法CSS3 新增长度单位CSS3 新增颜色设置方式CSS3 新增选择器CSS3 新增盒模型相关属性box-sizing 怪异盒模型resize调整盒子大小box-shadow 盒子阴影opacity 不透明度 CSS3 新增背景属性ba…...