2020年薪30W的Java程序员都要求熟悉JVM与性能调优!

前言

作为Java程序员,你有没有被JVM伤害过?面试的时候是否碰到过对JVM的灵魂拷问?

一、JVM 内存区域划分

1.程序计数器(线程私有)

程序计数器(Program Counter Register),也有称作为 PC 寄存器。保存的是程序当前执行的指令的地址(也可以说保存下一条指令的所在存储单元的地址),当 CPU 需要执行指令时,需要从程序计数器中得到当前需要执行的指令所在存储单元的地址,然后根据得到的地址获取到指令,在得到指令之后,程序计数器便自动加 1 或者根据转移指针得到下一条指令的地址,如此循环,直至执行完所有的指令。也就是说是用来指示执行哪条指令的。

由于在 JVM 中,多线程是通过线程轮流切换来获得 CPU 执行时间的,因此,在任一具体时刻,一个 CPU 的内核只会执行一条线程中的指令,因此,为了能够使得每个线程都在线程切换后能够恢复在切换之前的程序执行位置,每个线程都需要有自己独立的程序计数器,并且不能互相被干扰,否则就会影响到程序的正常执行次序。因此,可以这么说,程序计数器是每个线程所私有的。

在 JVM 规范中规定,如果线程执行的是非 native 方法,则程序计数器中保存的是当前需要执行的指令的地址;如果线程执行的是 native 方法,则程序计数器中的值是 undefined。

由于程序计数器中存储的数据所占空间的大小不会随程序的执行而发生改变,因此,对于程序计数器是不会发生内存溢出现象(OutOfMemory)的。

异常情况:

不存在

2.Java 栈(线程私有)

3.本地方法栈(线程私有)

4.堆(线程共享)

5.方法区(线程共享)

6.直接内存(线程共享)

二、JVM 执行子系统

1.Class 类文件结构

1.1 Java 跨平台的基础

各种不同平台的虚拟机与所有平台都统一使用的程序存储格式——字节码(ByteCode)是构成平台无关性的基石,也是语言无关性的基础。Java 虚拟机不和包括 Java 在内的任何语言绑定,它只与“Class 文件”这种特定的二进制文件格式所关联,Class 文件中包含了 Java虚拟机指令集和符号表以及若干其他辅助信息。

1.2 Class 类的本质

任何一个 Class 文件都对应着唯一一个类或接口的定义信息,但反过来说,Class 文件实际上它并不一定以磁盘文件的形式存在。Class 文件是一组以 8 位字节为基础单位的二进制流。

1.3 Class 文件格式

各个数据项目严格按照顺序紧凑地排列在 Class 文件之中,中间没有添加任何分隔符,这使得整个 Class 文件中存储的内容几乎全部是程序运行的必要数据,没有空隙存在。Class 文件格式采用一种类似于 C 语言结构体的伪结构来存储数据,这种伪结构中只有两种数据类型:无符号数和表。

无符号数属于基本的数据类型,以 u1、u2、u4、u8 来分别代表 1 个字节、2 个字节、4 个字节和 8 个字节的无符号数,无符号数可以用来描述数字、索引引用、数量值或者按照 UTF-8编码构成字符串值。

表是由多个无符号数或者其他表作为数据项构成的复合数据类型,所有表都习惯性地以“_info”结尾。表用于描述有层次关系的复合结构的数据,整个 Class 文件本质上就是一张表。

2.字节码指令

2.1 加载和存储指令

2.2 运算或算术指令

2.3 类型转换指令

2.4 创建类实例的指令

2.5 创建数组的指令

2.6 访问字段指令

2.7 数组存取相关指令

2.8 检查类实例类型的指令

2.9 操作数栈管理指令

2.10 控制转移指令

2.11 方法调用指令

2.12 方法返回指令

2.13 异常处理指令

2.14 同步指令

3.类加载机制

4.类加载器

4.1 系统的类加载器

4.2 双亲委派模型

5.Tomcat 类加载机制

6.方法调用详解

6.1 解析

6.2 静态分派

6.3 动态分派

6.4 基于栈的字节码解释执行引擎

三.垃圾回收器和内存分配策略

1.Java 中是值传递还是引用传递?

2.引用类型

3.基本垃圾回收算法

3.1.1 引用计数(Reference Counting):

比较古老的回收算法。原理是此对象有一个引用,即增加一个计数,删除一个引用则减少一个计数。垃圾回收时,只用收集计数为 0 的对象。此算法最致命的是无法处理循环引用的问题。

3.1.2 可达性分析清理

标记-清除(Mark-Sweep):此算法执行分两阶段。第一阶段从引用根节点开始标记所有被引用的对象,第二阶段遍历整个堆,把未标记的对象清除。此算法需要暂停整个应用,同时,会产生内存碎片。

复制(Copying): 此算法把内存空间划为两个相等的区域,每次只使用其中一个区域。垃圾回收时,遍历当前使用区域,把正在使用中的对象复制到另外一个区域中。次算法每次只处理正在使用中的对象,因此复制成本比较小,同时复制过去以后还能进行相应的内存整理,不会出现“碎片”问题。当然,此算法的缺点也是很明显的,就是需要两倍内存空间。

标记-整理(Mark-Compact):此算法结合了“标记-清除”和“复制”两个算法的优点。也是分两阶段,第一阶段从根节点开始标记所有被引用对象,第二阶段遍历整个堆,清除标记对象,并未标记对象并且把存活对象“压缩”到堆的其中一块,按顺序排放。此算法避免了“标记-清除”的碎片问题,同时也避免了“复制”算法的空间问题。

3.1 按照基本回收策略分

3.2 按分区对待的方式分

3.3 按系统线程分

4.分代处理垃圾

5.JAVA 中垃圾回收 GC 的类型

四、编写高效优雅 Java 程序

1.面向对象

1.1 构造器参数太多怎么办?

用 builder 模式,用在

(1)5 个或者 5 个以上的成员变量

(2)参数不多,但是在未来,参数会增加

Builder 模式:

属于对象的创建模式,一般有

(1)抽象建造者:一般来说是个接口,包含

1)建造方法,建造部件的方法(不止一个)

2)返回产品的方法

(2) 具体建造者

(3) 导演者,调用具体的建造者,创建产品对象

(4)产品,需要建造的复杂对象

对于客户端,创建导演者和具体建造者,并把具体建造者交给导演者,然后由客户端通知导演者操纵建造者进行产品的创建。

在实际的应用过程中,有时会省略抽象建造者和导演者。

1.2 不需要实例化的类应该构造器私有

1.3 不要创建不必要的对象

1.4 避免使用终结方法

1.5 使类和成员的可访问性最小化

1.6 使可变性最小化

1.7 复合优先于继承

1.8 接口优于抽象类

2.方法

2.1 可变参数要谨慎使用

2.2 返回零长度的数组或集合,不要返回 null

2.3 优先使用标准的异常

3.通用程序设计

五、性能优化

一个 web 应用不是一个孤立的个体,它是一个系统的部分,系统中的每一部分都会影响整个系统的性能

1.常用的性能评价/测试指标

1.1 响应时间

提交请求和返回该请求的响应之间使用的时间,一般比较关注平均响应时间。

常用操作的响应时间列表:

1.2 并发数

同一时刻,对服务器有实际交互的请求数。

和网站在线用户数的关联:1000 个同时在线用户数,可以估计并发数在 5%到 15%之间,也就是同时并发数在 50~150 之间。

1.3 吞吐量

对单位时间内完成的工作量(请求)的量度

1.4 关系

系统吞吐量和系统并发数以及响应时间的关系:

理解为高速公路的通行状况:

吞吐量是每天通过收费站的车辆数目(可以换算成收费站收取的高速费),并发数是高速公路上的正在行驶的车辆数目,响应时间是车速。车辆很少时,车速很快。但是收到的高速费也相应较少;

随着高速公路上车辆数目的增多,车速略受影响,但是收到的高速费增加很快;

随着车辆的继续增加,车速变得越来越慢,高速公路越来越堵,收费不增反降;

如果车流量继续增加,超过某个极限后,任务偶然因素都会导致高速全部瘫痪,车走不动,当然后也收不着,而高速公路成了停车场(资源耗尽)。

2.常用的性能优化手段

2.1 避免过早优化

2.2 进行系统性能测试

2.3 寻找系统瓶颈,分而治之,逐步优化

2.4 前端优化常用手段

3 应用服务性能优化

3.1 缓存

3.1.1 缓存的基本原理和本质

3.1.2 合理使用缓冲的准则

3.1.3 分布式缓存与一致性哈希

3.2 异步

3.2.1 同步和异步,阻塞和非阻塞

3.2.2 常见异步的手段

3.3 集群

3.4 应用相关

3.4.1 代码级别

3.4.2 并发编程

3.4.3 资源的复用

3.4.4 JVM

3.4.5 GC 调优

3.4.6 调优实战

3.4.7 存储性能优化

上面的这些问题只是给大家一个借鉴作用,最主要的是给自己增加知识的储备,有备无患。

关于JVM与性能调优总结了将近50页pdf文档,欢迎关注我的公种浩:程序员追风,获取这些整理的资料!

希望能帮助到你面试前的复习且找到一个好的工作,也节省大家在网上搜索资料的时间来学习。

最后

欢迎大家一起交流,喜欢文章记得关注我点个赞哟,感谢支持!

原文地址:https://www.cnblogs.com/zhuifeng523/p/12260677.html

时间: 2024-08-11 18:26:33

2020年薪30W的Java程序员都要求熟悉JVM与性能调优!的相关文章

为什么很多Java程序员都转行做大数据了?

如今大数据发展的越来越成熟.各大企业纷纷成立大数据部门.尤其BAT等一线互联网公司每天处理的数据量都是TB级别.大数据部门已成为这些企业的核心部门,数据已成为企业最核心的资产. 但是大数据人才缺口巨大,据统计目前全国的大数据人才仅46万,未来3-5年内大数据人才的缺口将高达150万. 因此大数据工程师薪资也比其他职位高出不少.以北京为例.1-3年的大数据工程师平均年薪30-50万,3-5年经验的大数据工程师年薪在50-80万.想学习的同学欢迎加入大数据学习扣群:458345782,有大量干货(零

分享:想要成为Java程序员都需要掌握哪些技术?

随着<2018年中国大学生就业报告>出炉,计算机相关专业的高就业率引起了人们的关注.为了能够实现高薪,越来越多的非专业人士转行从事编程开发,Java作为最受欢迎的编程语言成为人们的一致选择! 想要成为一名优秀的Java程序员,不能像无头苍蝇一样乱转,一些关键技术的掌握是非常重要的,比如说×××老师分享的这九点: 一.熟练的使用Java语言进行面向对象程序设计,有良好的编程习惯,熟悉常用的JavaAPI,包括集合框架.多线程(并发编程).I/O(NIO).Socket.JDBC.XML.反射等.

JAVA程序员养成计划之JVM学习笔记(3)-JVM性能监控

本文对JVM的性能监控方法做整理. 持续更新中- - 1. JDK命令行工具 1.1. jps:虚拟机进程状况工具 JVM Process Status Tool, 显示系统内所有的HotSpot虚拟机进程,用于查看当前在jvm中运行的程序,包括虚拟机执行主类的名称以及进程ID. 1.2. jstat:虚拟机统计信息监视工具 JVM Statistics Monitoring Tool, 用于收集Hotspot虚拟机各方面的运行数据,包括类装载.内存.垃圾收集.JIT编译等运行数据. 1.3.

JAVA程序员养成计划之JVM学习笔记(2)-垃圾收集管理

本文对JVM垃圾收集进行说明,包括三种不同算法(标记复制.标记清除.标记整理),以及七种不同的垃圾收集器(Serial,ParNew,Serial Scavenge, CMS, Serial Old, Parallel Old, G1) 持续更新中- - 1. 垃圾回收相关概念 1.1. 垃圾回收对象 说到垃圾收集,首先得确定哪些是可回收的对象,这里涉及到java的四种引用方式,即强.软.弱.虚四类引用. 强引用:即普遍存在的对对象的引用,如指向通过new创建的对象 软引用:即程序运行非必须的对

微信熟人牛牛程序安装微信熟人牛牛程序安装2017年 Java 程序员,风光背后的危机

不得不承认,经历过行业的飞速发展期微信熟人牛牛程序安装(h5.hxforum.com) 联系方式170618633533企鹅2952777280源码出售 房卡出售 后台出租有意者私聊扣扣,互联网的整体发展趋于平稳.为什么这么说?为什么要放在 Java 程序员的盘点下说?的确,对于进可攻前端,后可守后端大本营的 Java 程序员而言,虽然供应逐年上涨,但是市场似乎对他们依然青睐有加.这些承担着技术招聘市场中高供给高需求的 Java 程序员在 17 年的招聘市场上,真的还能如此风光吗?还是埋下了一些

Java程序员可能犯的3个常见SQL错误

概述:Java程序员不仅要具备扎实的Java编程能力,在日常的工作当中往往还要涉及到其他语言的基础知识,尤其是SQL.那么哪些常见的SQL错误是程序员们容易犯的呢?让我们一起来看看吧! 你可能看到Java程序员每周的工作是编码开发一个可伸缩的Web应用程序,或创建一个动态的网站,或者开发高效的电子商务产品页面,也可能是开发一个Android应用程序等等.但是,即使他们致力于不同的项目,却往往都有一个共同点,那就是编程! 他们的职业要求长时间的工作来积累更多的编程知识.Java程序员还需要了解项目

【转】你离顶尖 Java 程序员,只差这11本书的距离

个人认为看书有两点好处: 能出版出来的书一定是经过反复的思考.雕琢和审核的,因此从专业性的角度来说,一本好书的价值远超其他资料 对着书上的代码自己敲的时候方便 "看完书之后再次提升自我的最好途径是看一些相关的好博文",我个人认为这是学习的第二步,因为一本书往往有好几百页,好的博文是自己看书学习之后的一些总结和提炼,对于梳理学习的内容很有好处,当然这里不是说自己的学习方法,就不再扯下去了. 很多程序员们往往有看书的冲动,但不知道看哪些书,下面我就给各位Java程序猿们推荐一些好书(每本书

每个程序员都必读的12篇文章

英文原文:10 Articles Every Programmer Must Read 作为一名 Java 程序员和软件开发人员,那些每个程序员都应该知道的 XXX 的文章教会了我不少东西,它们提供了某个特定领域的一些实用的并且有深度的信息,这些东西通常很难找到.在我学习的过程中我读到过许多非常有用的文章,我把它们添加到了书签里,方便以后阅读或者引用.我个人认为所有开发人员都能从这些文章中受益,因此我也写了篇"每个程序员都应该了解的"文章,准备分享给你们.这是我的个人收藏.在这篇文章中

JAVA程序员必看11本书籍

http://developer.51cto.com/art/201512/503095.htm 学习的最好途径就是看书",这是我自己学习并且小有了一定的积累之后的第一体会.个人认为看书有两点好处: 1.能出版出来的书一定是经过反复的思考.雕琢和审核的,因此从专业性的角度来说,一本好书的价值远超其他资料 2.对着书上的代码自己敲的时候方便 "看完书之后再次提升自我的最好途径是看一些相关的好博文",我个人认为这是学习的第二步,因为一本书往往有好几百页,好的博文是自己看书学习之后