jvm调优

 一 程序员的战场(内存空间)

         自从c与c++换成用java开发后发现写代码的速度大大提升而难度也大大的降低了,但发现对内存的管理开始模糊了,心里总有疑问写的东西运行时会占用了多少内存空间?内存占用空间可以说一直是对开发者非常重要,很多时候就觉得它就是战场,无论是什么开发语言都应该要撑控,而java开发由于是jvm管理内存,所以jvm调优应该每一个java程序员应该熟练的知识。

二 进行jvm调优要先知道代码所占用的内存

在Java中,查看一个变量、方法或类(对象)占用的内存空间并不直观,因为Java虚拟机(JVM)对内存分配是基于对象实例进行的。变量本身不直接占用内存,而是它们所引用的对象占用内存。以下是一些分析和估算的方法:

  1. 单个变量

    • 基本类型的变量(如int、char等)会占用固定的内存大小,与具体的值无关。
    • 对象引用类型的变量(如String、List等),该变量自身只存储一个指向对象的引用,其大小通常是固定的,通常为32位或64位环境下的4字节或8字节。
  2. 方法

    • 方法本身不占用运行时内存,它只存在于类的元数据中,执行方法时占用的是调用栈和方法内部创建的局部变量及临时对象的内存。
    • 如果想要了解方法执行过程中消耗了多少内存,可以通过性能分析工具(如VisualVM)监控堆内存变化,或者使用内存分析工具分析方法执行前后的堆转储文件,找出由该方法创建或影响的所有对象及其占用的内存。
  3. 类或对象占用的空间

    • 类实例占用的内存包括:
      • 对象头:包含类型指针、锁状态标志、哈希码等信息,大小与平台相关。
      • 实例字段:每个字段占用的空间取决于其类型。
      • 对齐填充:为了满足特定硬件平台上内存对齐的要求,可能会有额外的填充字节。
    • 使用java.lang.instrument.Instrumentation接口可以在运行时获取对象大小,但需要通过特殊的手段注入到应用中,例如前面提到的代理类方式。
    • 另外,可以使用第三方库如JOL (Java Object Layout) 来解析类的内存布局,但它并不会提供实际运行时的数据,而是给出理论上的内存布局。

 获取内存大小方式:

使用java.lang.instrument.Instrumentation接口获取Java对象的内存大小,首先需要创建一个代理类,并在JVM启动时通过 -javaagent 参数注入 ,代码如下:

import java.lang.instrument.Instrumentation;/**
* 获取内存大小
*/
public class MemoryAgent {private static volatile Instrumentation instrumentation;public static void premain(String agentArgs, Instrumentation inst) {instrumentation = inst;}public static long getObjectSize(Object obj) {if (instrumentation != null) {return instrumentation.getObjectSize(obj);} else {throw new IllegalStateException("未初始化!");}}
}

 编译该代理类并打包成jar文件(例如:memory-agent.jar)。

 在运行Java应用程序时,通过 -javaagent 参数指定代理类和jar包的位置:

java -javaagent:path/to/memory-agent.jar -jar your-application.jar

 在应用中,就可以调用MemoryAgent.getObjectSize()来获取对象的内存占用大小了

public class Main {public static void main(String[] args) {String testStr = "Hello, World!";// 获取字符串对象的内存占用大小long size = MemoryAgent.getObjectSize(testStr);System.out.println("The size of the string object is: " + size + " bytes");}
}

说明:getObjectSize()返回的是特定平台上的对象大小,包括对象头、实例数据以及对齐填充等部分,但不包括任何对象引用的对象本身所占用的内存。如果对象间存在复杂的引用关系,可能需要更复杂的分析工具来了解整个内存占用情况。 

三 JVM调优

JVM调优基础是指对Java虚拟机(JVM)进行性能优化的基本原理和步骤,它涉及到多个方面,包括但不限于内存管理、垃圾回收策略、线程管理和编译器优化等。以下是JVM调优的一些基本知识点:

  1. 内存管理与GC调优

    • 堆内存划分:Java堆内存通常被划分为新生代(Young Generation)、老年代(Old Generation)和元空间(Metaspace或PermGen在较早版本中)。
    • 内存分配策略:新创建的对象首先在Eden区分配,经过一定次数的Minor GC后,仍存活的对象会被晋升到老年代。
    • GC类型选择:根据应用特点选择合适的垃圾回收器,如Serial、Parallel、CMS、G1或者ZGC、Shenandoah等,并针对所选GC调整相关参数。
    • 调优指标:关注Full GC频率、STW时间、吞吐量以及内存碎片化等问题。
  2. JVM参数设置

    • -Xms 和 -Xmx:设定初始和最大堆大小。
    • -XX:NewRatio:控制新生代与老年代的比例。
    • -XX:SurvivorRatio:新生代中eden与survivor空间的比例。
    • -XX:+UseConcMarkSweepGC 或 -XX:+UseG1GC 等:指定垃圾收集器。
    • -XX:MaxTenuringThreshold:对象在新生代中经历多少次Minor GC后晋升至老年代的阈值。
  3. 监控与诊断工具

    • 使用jconsole、VisualVM、JMC等工具进行实时系统监控,查看CPU使用率、内存占用、线程状态、垃圾回收情况等。
    • 分析GC日志,了解GC事件的发生频率和影响。
  4. 代码优化

    • 降低对象分配频率和减少短生命周期对象的数量,避免过多的内存分配压力。
    • 合理设计数据结构以提高内存利用效率,比如尽量重用对象,减少临时对象的生成。
  5. 线程与并发优化

    • 调整线程池大小,避免过高的线程切换开销。
    • 优化锁机制,减少锁竞争,例如使用更高效的并发容器或无锁数据结构。
  6. JIT即时编译优化

    • 利用JVM的热点代码探测和即时编译功能来提升运行时性能。

常见的调优指标是降低全gc的次数, 涉及最常用的调优参数是-Xms 和 -Xmx。

总的来说,JVM调优是一个综合性的过程,需要结合具体应用场景、业务需求以及硬件资源状况,通过分析监控数据、合理配置JVM参数以及优化代码实现性能提升。调优过程中要注意权衡不同的性能指标,如响应时间、吞吐量和内存使用效率等。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/588848.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

怎么解决 Nginx反向代理加载速度慢?

Nginx反向代理加载速度慢可能由多种原因引起,以下是一些可能的解决方法: 1,网络延迟: 检查目标服务器的网络状况,确保其网络连接正常。如果目标服务器位于不同的地理位置,可能会有较大的网络延迟。考虑使用…

Good Bye 2023

Good Bye 2023 Good Bye 2023 A. 2023 题意:序列a中所有数的乘积应为2023,现在给出序列中的n个数,找到剩下的k个数并输出,报告不可能。 思路:把所有已知的数字乘起来,判断是否整除2023,不够…

ajax 下载文件(excel导出)

<button class"btn btn-danger m-r-5" id"exportClick" style"width: 100px;margin-left:10px;">日报表</button> ajax 请求后端 $("#exportClick").click(function () {var url ${basePath}/rest/cart/exportconsole.l…

Android Studio如何创建尺寸大小及API通用的模拟器

目录 前言 一、操作步骤 二、总结 三、更多资源 前言 在开发移动应用程序的过程中&#xff0c;使用模拟器进行测试是一种常见和方便的方式。Android Studio是一款功能强大的集成开发环境&#xff0c;它提供了创建和管理模拟器的功能。在本文中&#xff0c;我们将介绍如何创…

qs.stringify 使用arrayFormat属性 + allowDots的数据处理 - 附示例

qs&#xff1a;将url中的参数转为对象&#xff1b;将对象转为url参数形式 一、介绍 1、官方文档&#xff1a; https://github.com/ljharb/qs https://github.com/ljharb/qshttps://github.com/ljharb/qs 二、准备工作 1、安装依赖包 npm install qs --save 2、示例版本 &…

英飞凌TC3xx之一起认识GTM系列(六)如何实现GTM与VADC关联的配置

英飞凌TC3xx之一起认识GTM系列(六)如何实现GTM与VADC关联的配置 1 GTM与ADC的接口2 GTM与VADC的连接2.1 VADC 到 GTM 的连接2.1.1 简要介绍2.1.2 应用举例2.2 EVADC到 GTM的连接2.2.1 应用举例3 总结本文介绍实现GTM与VADC的连接性的相关寄存器配置。 1 GTM与ADC的接口 由英…

Autodesk Maya各版本安装指南

链接地址如下&#xff1a; https://pan.baidu.com/s/1Fg7MvUJS0tl5t2XAwMK9xg?pwd0531 1.鼠标右击【Maya2024(64bit)】压缩包&#xff08;win11及以上系统需先点击“显示更多选项”&#xff09;【解压到 Maya2024(64bit)】。 2.打开解压后的文件夹&#xff0c;双击打开【Setu…

vue-springboot基于JavaWeb的宠物店兽医站管理系统

ide工具&#xff1a;IDEA 或者eclipse 编程语言: java 数据库: mysql5.7 框架&#xff1a;ssmspringboot都有 前端&#xff1a;vue.jsElementUI 详细技术&#xff1a;HTMLCSSJSspringbootSSMvueMYSQLMAVEN 数据库工具&#xff1a;Navicat结合现有兽医站体系的特点&#xff0c;运…

Android 实现 Slots 游戏旋转效果

文章目录 前言一、效果展示二、代码实现1.UI布局2.SlotAdapter2.SlotsActivity 总结 前言 slots游戏&#xff1a; Slots游戏是一种极具流行度的赌博和娱乐形式&#xff0c;通常被称为老虎机或水果机。它们在赌场、线上游戏平台和手机应用中广泛存在。一般这类游戏都使用Unity…

MySQL例行检查

MySQL例行检查 1.实例例行检查1.1线程1.2索引1.3临时表1.4连接数1.5BINLOG1.6锁1.7WAIT事件1.8MySQL状态 2.事务与锁例行检查2.1查看索引的cardinality2.2查看是否存在事务阻塞现象2.3查看事务执行时长以及执行的所有SQL2.4事务与锁 3.库表例行检查3.1查看缺失主键的表3.2冗余索…

C# 给方形图片切圆角

写在前面 在有些场景中&#xff0c;给图片加上圆角处理会让视觉效果更美观。 代码实现 /// <summary>/// 将图片处理为圆角/// </summary>/// <param name"image"></param>/// <returns></returns>private Image DrawTranspar…

自动驾驶学习笔记(二十四)——车辆控制开发

#Apollo开发者# 学习课程的传送门如下&#xff0c;当您也准备学习自动驾驶时&#xff0c;可以和我一同前往&#xff1a; 《自动驾驶新人之旅》免费课程—> 传送门 《Apollo开放平台9.0专项技术公开课》免费报名—>传送门 文章目录 前言 控制算法 控制标定 控制协议…

《深入理解JAVA虚拟机笔记》并发与线程安全原理

除了增加高速缓存之外&#xff0c;为了使处理器内部的运算单元能尽量被充分利用&#xff0c;处理器可能对输入代码进行乱序执行&#xff08;Out-Of-Order Execution&#xff09;优化。处理器会在计算之后将乱序执行的结果重组&#xff0c;保证该结果与顺序执行的结果一致&#…

PyTorch常用工具(1)数据处理

文章目录 前言1 数据处理1.1 Dataset1.2 DataLoader 前言 在训练神经网络的过程中需要用到很多的工具&#xff0c;最重要的是数据处理、可视化和GPU加速。本章主要介绍PyTorch在这些方面常用的工具模块&#xff0c;合理使用这些工具可以极大地提高编程效率。 由于内容较多&am…

Java-枚举

基本概念 数据类型&#xff1a; 基本数据类型&#xff1a;有8个引用数据类型&#xff1a;数组[]、类class、抽象类abstract class、接口、枚举enum、注解interface 枚举的应用场景&#xff1a; 当一个类中的对象是确定的时候&#xff0c;可以使用枚举&#xff0c;例如&#x…

C++ BuilderXE10 关于Intraweb关于IWTemplateProcessorHTML1操作

1、端口设置,port参数修改端口号。 2、初始化设置成ciMultiThreaded。这样可以避免ADO组件的加载错误。 3、IWTemplateProcessorHTML1设置&#xff0c; IWForm1->LayoutMgr IWTemplateProcessorHTML1;//关联模板(IWForm1. html) IWTemplateProcessorHTML1->RenderStyles…

很想写一个框架,比如,spring

很想写一个框架&#xff0c;比如&#xff0c;spring。 原理很清楚&#xff0c;源码也很熟悉。 可惜力不从心&#xff0c;是不是可以找几个小弟一起做。

缓存和数据库,1+1如何大于2?

一、缓存的本质 缓存&#xff0c;简单说就是为了节约对原始资源重复获取的开销&#xff0c;而将结果数据副本存放起来以供获取的方式。 首先&#xff0c;缓存往往针对的是“资源”。我们前面已经多次提到过&#xff0c;当某一个操作是"幂等"的和“安全"的&#…

2024年原创深度学习算法项目分享

原创深度学习算法项目分享&#xff0c;包括以下领域&#xff1a; 图像视频、文本分析、知识图谱、推荐系统、问答系统、强化学习、机器学习、多模态、系统界面、爬虫、增量学习等领域… 有需要的话&#xff0c;评论区私聊

C语言中的难点

C语言把内存划分成四个区&#xff0c;它把一般的变量和数组等存在于内存中的栈区&#xff0c;全局变量在静态区若指针没有被初始化,那么指针可能会指向任何内存位置,这样可能会导致程序崩溃或者行为不确定&#xff0c;野指针就是指针指向的位置是不可知的&#xff08;随机的、不…