java内存泄漏查找
java由于拥有自动垃圾回收机制,所以一般情况下,我们不需要考虑内存泄漏的问题。jvm会自动收回无用的对象。所谓无用的对象,表示你的程序不可能再访问的对象。但是,有一种情况必须考虑,就是要防止容器(List,Map等)内的对象无限增大。因为对象存贮在容器中,会被容器引用,从而如果容器的有效,容器内的对象就不会释放。一旦真的出现内存泄漏,随着时间的推移,java程序逐渐增大内存消耗,最后出现
java由于拥有自动垃圾回收机制,所以一般情况下,我们不需要考虑内存泄漏的问题。jvm会自动收回无用的对象。所谓无用的对象,表示你的程序不可能再访问的对象。
但是,有一种情况必须考虑,就是要防止容器(List,Map等)内的对象无限增大。因为对象存贮在容器中,会被容器引用,从而如果容器的有效,容器内的对象就不会释放。
一旦真的出现内存泄漏,随着时间的推移,java程序逐渐增大内存消耗,最后出现OutOfMemory异常而终止。
如何查找内存泄漏?
这种情况下,一般需要找到内存泄漏的对象。也就是要找到哪个对象数量最大。我们可以利用java SDK 自带的工具 jmap
在命令行中输入: jmap -histo:live [java进程id]>C:Log.txt
例如:如果当前内存泄漏的程序进程id是 3696,但是进程还没有终止。这个时候,可以在命令行中输入 jmap -histo:live 3696>C:\\Log.txt
这样会将结果输入到C:\\Log.txt文件中,应写字板打开,可以看到对象数量以及占用内存情况:
num #instances #bytes class name
----------------------------------------------
1: 34637921 1385516840 World.GameMap$ChangeTunAction
2: 17093 172636824 [Ljava.lang.Object;
3: 441074 140380032 [C
4: 439899 10557576 java.lang.String
5: 48858 8277760 [I
6: 60774 2917152 java.util.TreeMap
7: 84480 2703360 World.Task.GameTaskLevelUpVIP
8: 55968 2238720 World.Task.GameTaskPassLevel
9: 63979 2047328 java.util.LinkedList
10: 46754 1496128 java.util.HashMap$Node
11: 60767 1458408 core.Timer
12: 34848 1393920 World.Task.GameTaskLogin
13: 1056 1334784 [LWorld.Task.GameTask;
......
以上日志可以看出,World.GameMap.ChangeTunAction类的实例数量有34637921个,占用内存1.28G,因此可以断定,是这个类的对象没有释放造成内存泄漏。
查找源程序相关代码,可以迅速找到出错位置。
更多推荐
所有评论(0)