调用HashMap.clear()会减少内存吗?为何实测内存下降?
问题分析:HashMap.clear()后内存减少的原因
测试代码
System.gc(); System.out.println((Runtime.getRuntime().totalMemory()-Runtime.getRuntime().freeMemory())/1024/1024);// print 1M Map map=new HashMap(); for(int i=0;i<100000;i++){ map.put("key"+i,"i"); } System.gc(); System.out.println((Runtime.getRuntime().totalMemory()-Runtime.getRuntime().freeMemory())/1024/1024); //print 10M map.clear(); System.gc(); System.out.println((Runtime.getRuntime().totalMemory()-Runtime.getRuntime().freeMemory()));//print less than 1M
疑问
从上述代码执行结果来看,调用clear方法后内存似乎有所减少。但查阅其他资料发现,clear方法并不会收缩HashMap的容量,那么为何内存会减少呢?
解答
这是因为内存减少的核心是键值对对象被回收,而非HashMap自身容量收缩:
HashMap.clear()的逻辑是遍历内部的table数组,把每个位置的Entry引用置为null,但不会改变table数组的长度——这就是所谓的“不收缩容量”。- 但之前存入的10万个
key("key"+i字符串)和value("i"字符串),原本通过Entry对象被HashMap持有引用,clear后这些引用被切断,GC时就会把这些字符串对象回收,这部分正是之前占用10M内存的主体。 - 调用clear后,剩余的内存占用只是HashMap的空table数组、负载因子等内部元数据,这部分内存量很小,远低于存满键值对时的占用,所以你会看到内存降到1M以下。
简单总结:clear释放的是业务数据(键值对)的内存,HashMap自身的结构内存还保留着,但前者才是内存消耗的大头,所以整体内存会明显下降。
内容的提问来源于stack exchange,提问作者Ran
相关产品推荐
相关产品推荐

