前言

java的内存分配和垃圾回收往往是影响系统性能和并发能力的主要因素,虚拟机提供许多的参数就是为了根据不同环境和请教下进行调优,没有最好的调优也没有固定的调优。需要我们深入的去了解jvm的各个垃圾回收机制和内存分配等知识。在java运行内存区域里面,java虚拟机栈、程序计数器、本地方法栈这3个伴随着线程生或者灭,是具备确定性的,所以我们主要研究java堆上面的这块内存怎么分配和回收。

判断对象存活的方法

  • 1 引用计数法:这个经典的对象存活判定算法的思路主要是给一个对象添加一个引用计数器,每当有一个引用该计数器就+1,而当一个引用失效时该计数器就-1,最后在任何时刻一旦该对象的引用计数器为0的时候该对象就不能使用。但是java里面并非采用该算法,因为该算法无法解决对象之间的相互引用的问题,也就无法导致相互引用的对象无法被GC。
  • 2 可达性分析法:商业语言例如java、c#都是采用一个“GC roots”的对象来判定该对象在一系列的引用链中不可达时,就判定该对象是不可用的,这些对象就被认为需要回收。(但是一个对象的真正销毁需要经历两次标记过程)如下图示意;

** java中有4种可以作为GC Roots的对象

  • 虚拟机栈中引用的对象
  • 方法区类静态属性引用的对象
  • 方法区常量引用的对象
  • 本地方法栈中JNI引用的对象

java的引用分类

  • 1 强引用 类似 Object o = new Object();这类引用在代码广泛存在的, GC是不会回收的
  • 2 软引用 存在一些有用但非必须的对象,在系统发生内存溢出异常强,这些对象列入第二次回收的范围
  • 2 弱引用 非必需对象且只能生存到下次GC发生之前
  • 3 虚引用 又称虚灵引用和幻影引用,一个对象设置成了虚引用的唯一目的就是当该对象被GC时收到一个系统通知

回收方法区

根据jvm虚拟机而言,其实一次GC能将堆中70~95%空间回收。但是方法区的废弃常量和无用的类都需要被回收。
无用的类,满足下面3个条件:

  • 1 该类的实例已经被回收,java堆不存在任何该类的实例
  • 2 加载该类的classloader已经被回收
  • 3 该类对于的java.lang.Class对象没有被引用,也就是无法用反射访问该类的方法。

** 垃圾收集算法

  • 1 标记-清除:首先标记出需要清除的对象,标记后统一回收。存在了效率问题 和内存空间碎片化的问题!
  • 2 复制算法:为了解决效率问题,复制算法将内存划分多块,一块满了之后复制到一块空的上面,然后回收完满的那块。在商业虚拟机里面,堆内存的新生代被分为了 一个Eden和2块Survivor区域,HotSpot默认Eden:survivor=8:1也就是说新生代的90%内存是可用内存,回收时将Eden和survivor复制到另一块survivor区域,然后再清理,如果超过了10%的话就需依赖其他内存区域如老年代。
  • 3 标记-整理算法:加入复制算法里面有一种极端情况如对象存活率很高的情况下,复制操作算法很低,就特定设计出将标记清除算法后,先将存活对象向另一端移动,然后清掉边界外的内存,这就是标记-整理算法避免了高对象存活率复制的低效率。
  • 4 分代收集算法:商业虚拟机垃圾收集采用分代收集算法,其实就是分为老年代采用标记-清理或者标记-整理,而新生代只有少量对象就采用复制算法。

** 垃圾收集器

Java Web 深入分析(12) JVM(2) 垃圾收集与内存分配的更多相关文章

  1. 深入理解JVM(5)——垃圾收集和内存分配策略

    1.垃圾收集对象 垃圾收集主要是针对堆和方法区进行. 程序计数器.虚拟机栈和本地方法栈这三个区域属于线程私有的,只存在于线程的生命周期内,线程结束之后也会消失,因此不需要对这三个区域进行垃圾回收. 哪 ...

  2. 了解JVM运行时的内存分配

    了解JVM运行时的内存分配 前言 上文中,在介绍运行时数据区域中的 JAVA 堆时,提到了 JVM 中的堆,一般分为三大部分:新生代.老年代.永久代,本文将进一步了解运行时的内存分配情况. 正文 1. ...

  3. C++ primer plus读书笔记——第12章 类和动态内存分配

    第12章 类和动态内存分配 1. 静态数据成员在类声明中声明,在包含类方法的文件中初始化.初始化时使用作用域运算符来指出静态成员所属的类.但如果静态成员是整形或枚举型const,则可以在类声明中初始化 ...

  4. Java Web 深入分析(6) Tomcat

    tomcat是什么:汤姆猫?Javaweb服务器? Tomcat是Apache 软件基金会(Apache Software Foundation)的Jakarta 项目中的一个核心项目,由Apache ...

  5. Java Web 深入分析(5) Java ClassLoader 工作机制

    Classloader 有3个作用 将class加载到JVM中去 审查每个类由谁去加载,是一种父优先的等级加载 把Class字节码统一编译成JVM统一要求的对象格式 ClassLoader的等级加载机 ...

  6. jvm(2):垃圾收集和内存分配

    typora-root-url: ./ 垃圾收集 垃圾收集器关注的是线程共享的这部分内存. jvisualvm用来监控JVM的运行情况,可以用它来查看和浏览Heap Dump.Thread Dump. ...

  7. 深入理解Java虚拟机二:垃圾收集与内存分配

    垃圾收集:垃圾收集要完成三件事,包括哪些内存需要回收,什么时候回收及如何回收. 1.需要回收的内存判定:没有引用指向原先分配给某个对象的内存时,则该内存是需要回收的垃圾 Java垃圾收集器在对内存进行 ...

  8. Java调优之jvm和线程的内存分析

    本文来源于铁木箱子的博客http://www.mzone.cc 这几天因为自己开发的一个网站在768M内存的机器上撑不起100多个用户的运行,因为每个用户启用功能后,系统将为每个用户分配8个左右的独立 ...

  9. 《深入理解java虚拟机》读书笔记——垃圾收集与内存分配策略

    可回收判定两种算法 引用计数法(Reference Counting):引用为0时可回收. 可达性分析法(Reachability Analysis): 从GCRoots对象到这个对象不可达. GCR ...

随机推荐

  1. webpack系列之安装(Mac OS)

    1. webpack介绍,可参考Webpack中文文档 2. 安装webpack之前先需要安装npm,可参看NPM的使用介绍 3. 安装webpack,可参考Webpack入门教程 ========= ...

  2. eclipse juno 怎么安装maven

    步骤如下: 1.下载maven的bin,在apache官方网站可以下载. 2.下载下来之后,解压,找个路径放进去, 把bin的位置设在环境变量里,新建环境变量MAVEN_HOME. 3.在PATH里加 ...

  3. Koa Cookie 的使用

    Cookie 简介 cookie 是存储于访问者的计算机中的变量.可以让我们用同一个浏览器访问同一个域 名的时候共享数据. HTTP 是无状态协议.简单地说,当你浏览了一个页面,然后转到同一个网站的另 ...

  4. hangfire控制台应用程序中添加控制面板

    1.使用nuget 管理包安装 Microsoft.AspNet.WebApi.OwinSelfHost 2.根目录添加新建类 名为:Startup.cs public class Startup { ...

  5. python selenium chrome 实现自动化登录

    1.环境安装 selenium的开发文档网址(英语好的可以直接看这个,写的很详细):http://selenium-python.readthedocs.io/ 因为实现的时候使用的是谷歌浏览器,在运 ...

  6. 【深入学习linux】系统分区与格式化

    分区:把大硬盘分为小的逻辑分区 格式化:写入文件系统 分区设备文件名:给每个分区定义设备文件名 挂载:给每个分区分配挂载点 分区->格式化->取名->分配挂载点(WINDOW下的盘弧 ...

  7. 清理收藏夹中的CSS

    1.去掉元素的属性, 例如宽度 #blog-calendar { width: initial !important; }

  8. BIM数据格式中IFC的标准及格式

    传统工程数据往往零散且片段的储存在各个不同的地方,数据格式也有各种不同的形式互相搭配,最常见的有图形(施工图.大样图.断面图.流程图等).文字(各种说明文件).数字(各种统计.数量或价格数据),这些数 ...

  9. Ehcache 学习入门

    目录 介绍 导入jar包 创建配置文件 第一个使用示例 配置文件解析 第一部分:CacheManager 第二部分:diskStore 第三部分:cache 总结 介绍 网上有很多关于Ehcache的 ...

  10. git初次登陆使用

    一. 安装git 二. 在当前项目根目录点击鼠标右键,出来下图: 点击进入git命令行界面. 三.初始化项目 git init 四. 添加所有文件到项目中 git add . 五. 尝试提交所有文件 ...