Java垃圾收集学习笔记
(1)除了释放不再被引用的对象,垃圾收集器还要处理 堆碎块 。请求分配新对象时可能不得不增大堆空间的大小,虽然可以使用的空闲空间是足够的,但是堆中没有没有连续的空间放得下新对象。可能会导致虚拟机产生不必要的”内存不足“错误。
(2)使用垃圾收集堆,有一个潜在的缺陷就是加大程序的负担, 可能影响程序的性能 。因为虚拟机需要追踪哪些对象被正在执行的程序引用,还要动态释放垃圾对象。
(3)程序可以调用System.gc()建议jvm去收集垃圾, 但是不能为垃圾回收机制指定某个对象是不是垃圾。即便调用了 gc() , 并不会马上进行垃圾回收 , 甚至不一定会执行垃圾回收 。所有的内存分配和回收权限都在jvm,不在开发人员手里。
可以试试:
public class RubbishRelease {
// 类的finalize方法,可以告诉垃圾回收器应该执行的操作,该方法从Object类继承而来。
// 在从堆中永久删除对象之前,垃圾回收器调用该对象的finalize方法。
public void finalize() {
System.out.println("the Object is going...");
}
public static void main(String[] args) {
for (int i = 0; i < 100; i++) {
// 下面不断创建对象,但是这些对象都没有被引用
new RubbishRelease();
new RubbishRelease();
new RubbishRelease();
System.gc();
}
System.out.println("The program is over!");
}
}
运行结果:

(4)垃圾收集算法有很多,但任何垃圾收集算法都必须做两件事情。首先,它必须检测出垃圾对象 。其次,它必须 回收垃圾对象所使用的堆空间并还给程序 。
(5)区分活动对象和垃圾的两个基本方法是 引用计数 和 跟踪 。
(6) 引用计数 是垃圾收集的早期策略。在这种方法中,堆中每一个对象都有一个引用计数。一个对象被创建了,并且指向该对象的引用被分配给一个变量,这个对象的引用计数被置为1。当任何其他变量被赋值为对这个对象的引用时,计数加1。当一个对象的引用超过了生存期或者被设置一个新的值时,对象的引用计数减1。任何引用计数为0的对象可以被当作垃圾收集。当一个对象被垃圾收集的时候,它引用的任何对象计数值减1。这种方法的好处是,引用计数收集器可以很快地执行,交织在程序的运行之中。这个特性对于程序不能被长时间打断的实时环境很有利。坏处就是,引用计数无法检测出循环(即两个或者更多的对象互相引用)。
(7) 跟踪收集器 追踪从根节点开始的对象引用图。给追踪过程中遇到对象以某种方式打上标记。追踪结束时,未被标记的对象就是无法触及的,从而被收集。基本的追踪算法被称作“ 标记并清除” ,这个名字指出垃圾收集过程的两个阶段。
(8)Java虚拟机的垃圾收集器可能有对付堆碎块的策略。标记并清除收集器通常使用的两种策略是 压缩 和 拷贝 。这两种方法都是快速地移动对象来减少堆碎块。
(9) 压缩收集器 把活动的对象越过空闲区滑动到堆的一端,在这个过程中,堆的另一端出现一个大的连续空闲区。所有被移动的对象的引用也被更新,指向新的位置。
(10) 拷贝收集器 把所有的活动的对象移动到一个新的区域。在拷贝过程中,被紧挨着布置,这样可以消除原本它们在旧区域的空隙。即空闲区。一般的拷贝收集器算法被称为“停止并拷贝”。此方案中,堆被分成两个区域,任何时候都使用一个区域。对象在同一个区域中分配直到被耗尽。此时,程序执行被中止,堆被遍历,遍历时遇到活动的对象被拷贝到另个区域。当停止和拷贝过程结束时,程序恢复执行。依次往复,对于指定大小的堆来说需要两倍大小的内存,由于任何时候都只使用其中的一半,这就是该方法带来的代价。
(11) 按代收集 :根据 对象的存活周期 (一次垃圾收集为一个周期)的不同将内存划分为几块。一般是把Java堆分为新生代和老年代,这样就可以根据各个年代的特点采用最适当的收集算法。在新生代中,每次垃圾收集时都发现有大批对象死去,只有少量存活,那就选用拷贝算法,只需要付出少量存活对象的拷贝成本就可以完成收集。而老年代中因为对象存活率高、没有额外空间对它进行分配担保,可以使用“标记并清除”算法。
(12) 终结方法 (finalize),这个在上面第3点也有提到:这个方法是垃圾收集器在释放对象前必须运行。这个可能存在的终结方法使得任何Java虚拟机的垃圾收集器要完成的工作更加复杂。因为终结方法可能“复活”了某些不再被引用的对象(本身或者其他对象)。
(13) 堆 中的每一个对象都有 三种状态 之一: 可触及的 、 可复活的 以及 不可触及的 。 可触及状态 好理解。关于 可复活状态 :它在从根节点开始的追踪图中不可触及,但是又可能在垃圾收集器执行某些终结方法时触及。不仅仅是那些声明了finalize方法的对象,而是所有的对象都要经过可复活状态。而 不可触及状态 标志着不但对象不再被触及,而且也不可能通过任何终结方法复活。不可触及的对象不再对程序的执行产生影响,可自由地回收它们占据的内存。
(14)对象的强,软,弱,虚引用。
强引用:如果一个对象具有强引用,垃圾回收器绝不会回收它。当内存空间不足,JVM宁愿抛出OutOfMemoryError错误,使程序异常终止,也不会考随意回收具有强引用的对象来解决内存不足的问题。
软引用:如果一个对象具有软引用。如果内存空间足够。垃圾回收器不会回收它。如果内存不足了,就会回收这些对象的内存。只要垃圾回收器没有回收它,该对象就可以被程序使用。软引用可用来实现内存敏感的高速缓存。
弱引用:如果一个对象具有弱引用。当垃圾回收器发现只具有弱引用对象,不管当前内存空间足够与否,都会回收它的内存。不过,由于垃圾回收器是一个优先级很低的线程,因此不一定会很快发现只具有弱引用的对象。
虚引用:虚引用不会决定对象的生命周期。如果一个对象仅持有虚引用,那么它就和没有任何引用一样,在任何时候都可能被垃圾回收器回收。
Java垃圾收集学习笔记的更多相关文章
- Java虚拟机学习笔记——JVM垃圾回收机制
Java虚拟机学习笔记——JVM垃圾回收机制 Java垃圾回收基于虚拟机的自动内存管理机制,我们不需要为每一个对象进行释放内存,不容易发生内存泄漏和内存溢出问题. 但是自动内存管理机制不是万能药,我们 ...
- 尚学堂JAVA基础学习笔记
目录 尚学堂JAVA基础学习笔记 写在前面 第1章 JAVA入门 第2章 数据类型和运算符 第3章 控制语句 第4章 Java面向对象基础 1. 面向对象基础 2. 面向对象的内存分析 3. 构造方法 ...
- 20145213《Java程序设计学习笔记》第六周学习总结
20145213<Java程序设计学习笔记>第六周学习总结 说在前面的话 上篇博客中娄老师指出我因为数据结构基础薄弱,才导致对第九章内容浅尝遏止地认知.在这里我还要自我批评一下,其实我事后 ...
- [原创]java WEB学习笔记95:Hibernate 目录
本博客的目的:①总结自己的学习过程,相当于学习笔记 ②将自己的经验分享给大家,相互学习,互相交流,不可商用 内容难免出现问题,欢迎指正,交流,探讨,可以留言,也可以通过以下方式联系. 本人互联网技术爱 ...
- java JDK8 学习笔记——助教学习博客汇总
java JDK8 学习笔记——助教学习博客汇总 1-6章 (by肖昱) Java学习笔记第一章——Java平台概论 Java学习笔记第二章——从JDK到IDEJava学习笔记第三章——基础语法Jav ...
- java JDK8 学习笔记——第16章 整合数据库
第十六章 整合数据库 16.1 JDBC入门 16.1.1 JDBC简介 1.JDBC是java联机数据库的标准规范.它定义了一组标准类与接口,标准API中的接口会有数据库厂商操作,称为JDBC驱动程 ...
- [原创]java WEB学习笔记75:Struts2 学习之路-- 总结 和 目录
本博客的目的:①总结自己的学习过程,相当于学习笔记 ②将自己的经验分享给大家,相互学习,互相交流,不可商用 内容难免出现问题,欢迎指正,交流,探讨,可以留言,也可以通过以下方式联系. 本人互联网技术爱 ...
- [原创]java WEB学习笔记66:Struts2 学习之路--Struts的CRUD操作( 查看 / 删除/ 添加) 使用 paramsPrepareParamsStack 重构代码 ,PrepareInterceptor拦截器,paramsPrepareParamsStack 拦截器栈
本博客的目的:①总结自己的学习过程,相当于学习笔记 ②将自己的经验分享给大家,相互学习,互相交流,不可商用 内容难免出现问题,欢迎指正,交流,探讨,可以留言,也可以通过以下方式联系. 本人互联网技术爱 ...
- Android(java)学习笔记267:Android线程池形态
1. 线程池简介 多线程技术主要解决处理器单元内多个线程执行的问题,它可以显著减少处理器单元的闲置时间,增加处理器单元的吞吐能力. 假设一个服务器完成一项任务所需时间为:T1 创建线程时间, ...
随机推荐
- ZeroClipboard / jquery.zclip.min.js跨浏览器复制插件使用中遇到的问题解决
之前写过一个淘宝优惠券连接PC端转手机端连接的小工具,当时写到将转换好的url复制到剪切板这块时解决了IE和火狐,就是没办法搞定Chrome,知道可以通过flash搞定,但是觉得太麻烦没有仔细研究. ...
- [POJ3696]The Luckiest number(数论)
题目:http://poj.org/problem?id=3696 题意:给你一个数字L,你要求出一个数N,使得N是L的倍数,且N的每位数都必须是8,输出N的位数(如果不存在输出0) 分析: 首先我们 ...
- php 升级php5.5
rpm -Uvh http://mirror.webtatic.com/yum/el6/latest.rpm yum install php55w php55w-opcache yum install ...
- 【JavaEE企业应用实战学习记录】struts配置文件详细解析
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE struts PUBLIC "-/ ...
- nginx中获取真实ip
nginx反向代理配置时,一般会添加下面的配置: proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; ...
- 用一条sql语句显示数据百分比并加百分号
来源于:http://neil-han.iteye.com/blog/1948124 求数值所占比重 关键点:(round(t1.cnt/t2.totalCount*100,2))||'%'
- Mahout安装与配置
一.安装mahout 1.下载mahout(mahout-distribution-0.9.tar.gz) http://pan.baidu.com/s/1kUtOMQb 2.解压至指定目录 我平时都 ...
- Ubuntu下tftp服务器的搭建
参考博客:http://blog.chinaunix.net/uid-26495963-id-3206829.html 1. 安装 $ apt-get install tftp-hpa tftpd-h ...
- java.lang.IndexOutOfBoundsException: Index: 0, Size: 0 错误
你的ArrayList 是一个没有值的对象(不是null),也就是里面什么对象也没有存(即:arrayList.size()==0).但是,你有取它下标为0值的操作.所以,数组越界了!!比如array ...
- 【CodeVS 3123】高精度练习之超大整数乘法 &【BZOJ 2197】FFT快速傅立叶
第一次写法法塔,,,感到威力无穷啊 看了一上午算导就当我看懂了?PS:要是机房里能有个清净的看书环境就好了 FFT主要是用了巧妙的复数单位根,复数单位根在复平面上的对称性使得快速傅立叶变换的时间复杂度 ...