GC的最根本緣由:垃圾收集器的工做就是清除Java建立的對象,垃圾收集器須要清理的對象數量以及要執行的GC數量均取決於已建立的對象數量。所以,爲了使你的系統在GC上表現良好,首先須要減小建立對象的數量。java
GC優化的兩個目的:算法
將進入老年代的對象數量降到最低數組
減小Full GC的執行時間瀏覽器
原則:服務器
設置內存大小,設置新老代比例,設置對象在新代的存活週期工具
找到最合理的老年代內存大小,性能
設置 CMS-Remark以前強制進行年輕代的GC,以下降remark時掃描的內存大小,下降STW的時間優化
若是經過減少老年代內存來減小Full GC時間,可能會引發 OutOfMemoryError
或者致使Full GC的頻率升高。spa
另外,若是經過增長老年代內存來下降Full GC的頻率,Full GC的時間可能所以增長。線程
設置好幾個參數並不會提高GC執行的速度,反而會使它變得更慢。
GC類型的選擇
-Xms
, -Xmx
設置堆內存大小
NewRatio:新生代和老年代的內存比,值設置得越大,則老年代空間越大,新生代空間越小。
可能會認爲把 NewRatio
設爲1會是最好的選擇,然而事實並不是如此,根據筆者的經驗,當 NewRatio
設爲2或3時,整個GC的狀態表現得更好。
/(-XX:NewSize 新生代大小)
-XX:SurvivorRatio Eden區和Survivor區的內存比
命令簡介:
jstat -gc pid 2000 20 (垃圾回收堆的行爲統計,每隔2000ms輸出一次,一共輸出20次)
S0C : survivor0區的總容量
S1C : survivor1區的總容量
S0U : survivor0區已使用的容量
S1C : survivor1區已使用的容量
EC : Eden區的總容量
EU : Eden區已使用的容量
OC : Old區的總容量
OU : Old區已使用的容量
PC 當前perm的容量 (KB)
PU perm的使用 (KB)
YGC : 新生代垃圾回收次數
YGCT : 新生代垃圾回收時間
FGC : 老年代垃圾回收次數
FGCT : 老年代垃圾回收時間
GCT : 垃圾回收總消耗時間
-gccapacity
同-gc,不過還會輸出Java堆各區域使用到的最大、最小空間
NGCMN : 新生代佔用的最小空間
NGCMX : 新生代佔用的最大空間
OGCMN : 老年代佔用的最小空間
OGCMX : 老年代佔用的最大空間
OGC:當前年老代的容量 (KB)
OC:當前年老代的空間 (KB)
PGCMN : perm佔用的最小空間
PGCMX : perm佔用的最大空間
-gcutil
同-gc,不過輸出的是已使用空間佔總空間的百分比
-gccause
垃圾收集統計概述(同-gcutil),附加最近兩次垃圾回收事件的緣由
LGCC:最近垃圾回收的緣由
GCC:當前垃圾回收的緣由
jmap(JVM Memory Map)命令用於生成heap dump文件,若是不使用這個命令,還能夠使用-XX:+HeapDumpOnOutOfMemoryError參數來讓虛擬機出現OOM的時候·自動生成dump文件。 jmap不只能生成dump文件,還闊以查詢finalize執行隊列、Java堆和永久代的詳細信息,如當前使用率、當前使用的是哪一種收集器等。
jmap -dump::live,format=b,file=<filename> pid
dump堆到文件,format指定輸出格式,live指明是活着的對象,file指定文件名
jmap -heap pid
打印heap的概要信息,GC使用的算法,heap的配置及wise heap的使用狀況,能夠用此來判斷內存目前的使用狀況以及垃圾回收狀況,能夠很清楚的看到Java堆中各個區域目前的狀況。
jmap -histo:live pic | more
打印堆的對象統計,包括對象數、內存大小等等 (由於在dump:live前會進行full gc,若是帶上live則只統計活對象,所以不加live的堆大小要大於加live堆的大小 ) class name簡寫以下:
B byte
C char
D double
F float
I int
J long
Z boolean
[ 數組,如[I表示int[]
[L+類名 其餘對象
jhat(JVM Heap Analysis Tool)命令是與jmap搭配使用,用來分析jmap生成的dump,jhat內置了一個微型的HTTP/HTML服務器,生成dump的分析結果後,能夠在瀏覽器中查看。在此要注意,通常不會直接在服務器上進行分析,由於jhat是一個耗時而且耗費硬件資源的過程,通常把服務器生成的dump文件複製到本地或其餘機器上進行分析。
jstack用於生成java虛擬機當前時刻的線程快照。線程快照是當前java虛擬機內每一條線程正在執行的方法堆棧的集合,生成線程快照的主要目的是定位線程出現長時間停頓的緣由,如線程間死鎖、死循環、請求外部資源致使的長時間等待等。 線程出現停頓的時候經過jstack來查看各個線程的調用堆棧,就能夠知道沒有響應的線程到底在後臺作什麼事情,或者等待什麼資源。 若是java程序崩潰生成core文件,jstack工具能夠用來得到core文件的java stack和native stack的信息,從而能夠輕鬆地知道java程序是如何崩潰和在程序何處發生問題。另外,jstack工具還能夠附屬到正在運行的java程序中,看到當時運行的java程序的java stack和native stack的信息, 若是如今運行的java程序呈現hung的狀態,jstack是很是有用的。
jinfo(JVM Configuration info)這個命令做用是實時查看和調整虛擬機運行參數。 以前的jps -v口令只能查看到顯示指定的參數,若是想要查看未被顯示指定的參數的值就要使用jinfo口令
jstat-gc
JVM的GC日誌的主要參數包括以下幾個:
-XX:+PrintGC
輸出GC日誌
-XX:+PrintGCDetails
輸出GC的詳細日誌
-XX:+PrintGCTimeStamps
輸出GC的時間戳(以基準時間的形式)
-XX:+PrintGCDateStamps
輸出GC的時間戳(以日期的形式,如 2017-09-04T21:53:59.234+0800)
-XX:+PrintHeapAtGC
在進行GC的先後打印出堆的信息
-Xloggc:../logs/gc.log
日誌文件的輸出路徑
在生產環境中,根據須要配置相應的參數來監控JVM運行狀況。
https://mp.weixin.qq.com/s/sFnMxEwJiYRjwTiBIjfcZg