众所周知 java的JVM有一套自己的垃圾回收机制 因此在许多情况下并不需要java程序开发人员 *** 太多的心 然而也许也因为这样 往往会造成java程序员的过分依赖而致使开发出来的程序得不到很好的优化 或者说性能尚能提高
问题的关键在于 不论JVM的垃圾回收机制做得多好 计算码核机的硬件资源是有限的 内存更是一项紧张资源 因此虽然JVM为我们完成了大部分的垃圾回收 但适当地注意编码过程中的内存管理还是很必要的 这样能让JVM回收得更顺利更高效 最大限度地提高程序的效率
mark 避免在循环体内创建对象吵帆
……
Object obj = null //方式一
for(int i = i k( k) secs]
……
可以看到总共有 kb的内存被回收 耗时 秒
JVM内存相关的参数
XX NewSize(Set the Newgeneralnation heap size)
XX MaxNewSize(Set the Maximum Newgeneralnation heap size)
XX SurvivorRatio(Set New heap size ratios)
Xms(Set minimum heap size)
Xmx(Set maximum heap size)
Xnoclassgc(取消垃圾回收)
Xss(设置栈内存的大小)
例 java XX NewSize = m XX MaxNewSize = m XX SurvivorRatio = Xms m Xmx m MyApplication
mark 不同编译方法的类大小
( )默认编译方式 javac K java
长度=代码+源文件信息+代码行序号表
( )调试编译方式 javac g K java
长度=代码+源文件信息+代码行序号表+本地变量表
( )代码编译方式 javax g none K java
长度=代码
mark 经验之谈
尽早释放无用对象的引用(XX = null )
尽量少使用finalize函数
注意集合数据类型 如数组 树 图 链表等数据结构 这些数据结构对GC来说回收更复杂
避免在类的默认构造器中创建大量的 初始化大量的对象
避免强制系统做垃圾升模雹内存回收
lishixinzhi/Article/program/Java/hx/201311/26273
从理论上来讲java做的系统并不比其他语言开发出来的系统更占用内存,那么为什么却有这么N多理由来证明它确实占内存呢?两个字,陋习。
(1)别用newBoolean()。
在很多场景中Boolean类型是必须的,比如JDBC中boolean类型的set与get都是通过Boolean封装传递的,大部分ORM也是用Boolean来封装boolean类型的,比如:
ps.setBoolean("isClosed",newBoolean(true))
ps.setBoolean("isClosed",newBoolean(isClosed))
ps.setBoolean("isClosed",newBoolean(i==3))
通常这些系统中构造的Boolean实例的个数是相当多的,所以系统中充满了大量Boolean实例小对象,这是相当消耗内存的。Boolean类实际上只要两个实例就够了,一个true的实例,一个false的实例。
Boolean类提供两了个静态变量:
publicstaticfinalBooleanTRUE=newBoolean(true)
publicstaticfinalBooleanFALSE=newBoolean(false)
需要的时候只要取这两个变量就可以了,
比如:
ps.setBoolean("isClosed",Boolean.TRUE)
那么像2、3句那样要根据一个boolean变量来创建一个Boolean怎么办呢?可以使用Boolean提供的静态方法:Boolean.valueOf()
比如:
ps.setBoolean("isClosed",Boolean.valueOf(isClosed))
ps.setBoolean("isClosed",Boolean.valueOf(i==3))
因为valueOf的内部实现是:return(b?TRUE:FALSE)
所以可以节省大量内存。相信如果Java规范直接把Boolean的构造函数规定成private,就再也不会出现这种情况了。
(2)别用newInteger.
和Boolean类似,java开发中使用Integer封装int的场合也非常多,并且通常用int表示的数值通常都非常小。SUNSDK中对Integer的实例化进行了优化,Integer类缓存了-128到127这256个状态的Integer,如果使用Integer.valueOf(inti),传入的int范围正好在此内,就返回静态实例。这样如果我们使用Integer.valueOf代替newInteger的话也将大大降低内存的占用。如果您的系统要在不同的SDK(比如IBMSDK)中使用的话,那么可以自己做了工具类封装一下,比如IntegerUtils.valueOf(),这样就可以在任何SDK中都可以使用这种特性。
(3)用StringBuffer代替字符串相加。
这个我就不多讲了,因为已经被人讲过N次了。我只想将一个不是笑话的笑话,我在看国内某“著名”java开发的WEB系统的源码中,竟然发现其中大量的使用字符串相加,一个拼装SQL语句的方法中竟然最多构造了将近100个string实例。无语中!
(4)过滥使用哈希表
有一定开发经验的开发人员经常会使用碰拦尘hash表(hash表在JDK中的一个实现就是HashMap)来缓存一些数据,从而提高系统的运行速度。比如java课程认为使用HashMap缓存一些物料信息、人员信息等基础资料,这在提高系统速度的同时也加大了系统的内存占用,特别是当缓存的资料比笑禅较多的时衡尘候。其实我们可以使用
1>在很多场景中Boolean类型是必须的,比销租如JDBC中boolean类型的set与get都是通过亏渗兆Boolean封装传递的,大部分ORM也是用Boolean来封喊瞎装boolean类型的2、别用new Integer
3、用StringBuffer代替字符串相加
4、过滥使用哈希表
5、尽量避免使用static变量
6、变量只有在用到它的时候才定义和实例化。
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)