java内存泄露一点点积累

来源:互联网 发布:wox python math 编辑:程序博客网 时间:2024/06/04 22:14

java中由于没有像c/c++ 那样,再使用完一个对象后,就手动的编写程序回收这个对象。

java里面的对象都是由java虚拟机的gc来完成的。

就像一个酒吧里面,假设酒吧里面有300个酒杯。然后酒吧里面来了100个人,每人要了一杯饮料,然后,就拿走了100个杯子,然后又来了60个人,每人要了一杯啤酒和一杯可乐,然后,就拿走了120个杯子,现在酒吧里的空闲杯子只有80个了,然后,过了一段时间,又来了90个人,每人要一杯啤酒,呃,发现,柜台里面的杯子不够了,但是那些最开始来的那些人,虽然喝完酒水离开了,但是他们的杯子还是在那里,随处都是,没有收回来清洗。gc,就相当于酒吧里面的杯子清洁员,他们将客人喝完酒水离开后,随意放置的那些杯子,倒吊剩余饮料,清洗消毒,然后放回柜台。比如,最后面来了90人,杯子不够,清理员将最开始来的100人中的某些离开了的顾客的杯子收过来,清理消毒,然后,放回柜台。然后,现在就有空余杯子了。类似于这么一个机制。如果客人走了,但是杯子不回收,一直放在那儿,这就是“杯子泄露”


简单的说,gc(垃圾回收)就是回收虚拟机内存中没有被引用的对象(强引用,软引用,虚引用,弱引用之类的),也就是上面那些客人走了但是没有被回收返回柜台的杯子。


package com.cn.wxwinnie.java.hashmap;import java.util.HashSet;import java.util.Set;/** * @author 潇湘暮雨 E-mail:wxwinnie@hotmail.com *  * @version 创建时间:2014年3月24日 下午1:42:31 *  */public class HashTest {public static void main(String[] args) {String ss1 = "aaaaaa";String ss2 = "bbbbbb";String ss3 = "cccccc";Set<String > ssset = new HashSet<String>();ssset.add(ss1); ssset.add(ss2); ssset.add(ss3); System.out.println("当前set大小为: "+ssset.size() + " hashcode:"+ ssset.hashCode());ss1 = "ssdsds";ssset.remove(ss1);System.out.println("当前set大小为: "+ssset.size()  + " hashcode:"+ ssset.hashCode());for(String str : ssset){System.out.println(str);}}}

执行结果为:

当前set大小为: 3 hashcode:107601472
当前set大小为: 3 hashcode:107601472
aaaaaa
bbbbbb
cccccc


像上面的ss1被重新赋值,然后调用set的remove方法就无效了(可以看到上面的HashCode都为107601472,也就是remove方法后set并没有发生变化,remove方法无效了)。不只是set,其他集合类也是这样的。

这里的cccccc占用的内存空间,假设我想回收,本来可以通过remove后来回收的,但是现在却不能了,因为此时的ss1的引用已经变了。要想回收,则需要销毁包含这个元素的集合对象。如果这里的集合对象是一个全局的,那么这样的话,就不好办了。




0 0