轉(zhuǎn)載自http://www.reibang.com/p/473c7b8b3bf3
Throwable
throwable類是所有的錯誤或異常的超類牲芋。只有對象是此類或其子類的實例之一時,才能通過JVM或者通過throw語句拋出。另外catch字句中的參數(shù)類型也必須是該類型缸浦。
Throwable包含兩個子類:Error和Excaption夕冲。他們通常用于指示發(fā)生了異常情況。Throwable類和子類的兩個構(gòu)造方法:
- 不帶參數(shù)
- 帶String參數(shù)
Exception
Exception及其子類是Throwable的一種形式餐济,它指出了合理的應(yīng)用程序要想捕獲的條件。對于可以恢復(fù)的條件使用“被檢查異车ň纾”(Exception的子類中除了RuntimeException之外的其他子類)絮姆,對于程序錯誤用“運行時異常”
RuntimeException
RuntimeException是那些可能在Java虛擬機正常運行期間拋出的異常的超類秩霍。編譯器不會檢查RuntimeException異常篙悯。例如,除數(shù)為0铃绒,拋出ArithmeticException異常鸽照。當(dāng)程序中可能出現(xiàn)這類異常時,還是會編譯通過颠悬。雖然java編譯器不會檢查運行異常矮燎,但是我們也可以通過throws進(jìn)行聲明拋出,也可以通過try-catch對它進(jìn)行捕獲處理赔癌。
Error
和Exception一樣诞外,Error也是Throwable的子類。它用于指示合理的應(yīng)用程序不應(yīng)該試圖捕獲的嚴(yán)重問題灾票,大多數(shù)這樣的錯誤都是異常條件峡谊。
和RuntimeException一樣,編譯器也不會檢查Error刊苍。
java可將可拋出(Throwable)的異常分為是3種類型:被檢查的異常(Checked Exception)既们、運行時異常(Runtime Exception)和錯誤(Error)
- 運行時異常
定義:RuntimeException 及其子類都被稱為運行時異常。
ArithmeticException:當(dāng)出現(xiàn)異常的運算條件時正什,拋出此異常啥纸。例如,一個整數(shù)“除以零”時婴氮,拋出此類的一個實例脾拆。
ClassCastException:當(dāng)試圖將對象強制轉(zhuǎn)換為不是實例的子類時,拋出該異常莹妒。例如:Object x = new Integer(0);
LllegalArgumentException:拋出的異常表明向方法傳遞了一個不合法或不正確的參數(shù)名船。
IllegalStateException:在非法或不適當(dāng)?shù)臅r間調(diào)用方法時產(chǎn)生的信號。換句話說旨怠,即Java環(huán)境或Java應(yīng)用程序沒有處于請求操作所要求的適當(dāng)狀態(tài)下渠驼。
IndexOutOfBoundsException:指示某排序索引(例如對數(shù)組、字符串或向量的排序)超出范圍時拋出鉴腻。 應(yīng)用程序可以為這個類創(chuàng)建子類迷扇,以指示類似的異常百揭。
NoSuchElementException:由Enumeration的nextElement方法拋出,表明枚舉中沒有更多的元素蜓席。
NullPointerException:當(dāng)應(yīng)用程序試圖在需要對象的地方使用null時器一,拋出該異常。這種情況包括:
調(diào)用null對象的實例方法厨内。
訪問或修改null對象的字段祈秕。
將null作為一個數(shù)組,獲得其長度雏胃。
將null作為一個數(shù)組请毛,訪問或修改其時間片。
將null作為Throwable值拋出瞭亮。
應(yīng)用程序應(yīng)該拋出該類的實例方仿,指示其他對null對象的非法使用。
被檢查的異常
定義:Exception類本身统翩,以及其子類除了運行時異常之外其他的子類都屬于被檢查異常仙蚜。
特點:java編譯器會檢查他,此類異常厂汗,要么通過throws進(jìn)行聲明描述鳍征,要么通過try-catch進(jìn)行捕獲處理,否則不能通過編譯面徽。例如艳丛,CloneNotSupportedException就屬于被檢查異常。當(dāng)通過clone()接口去克隆一個對象趟紊,而該對象對應(yīng)的類沒有實現(xiàn)Cloneable接口氮双,就會拋出CloneNotSupportedExeption異常,被檢查的異常通常都是可以恢復(fù)的霎匈。錯誤
定義:Error類及其子類
特點:和運行時異常一樣戴差,編譯器也不會對錯誤進(jìn)行檢查,當(dāng)資源不足铛嘱,約束失敗暖释、或是其他程序無法繼續(xù)運行發(fā)生的條件發(fā)生時,就產(chǎn)生錯誤墨吓。程序本身無法修復(fù)這些錯誤的球匕。例如,VirtuaMachineError就屬于錯誤帖烘。
OOM
1.OutOfMemoryError異常
除了程序計數(shù)器外亮曹,虛擬機內(nèi)存的其他幾個運行區(qū)域都有發(fā)生OutOfMemoryError(OOM)異常的可能。
java Heap 溢出
一般的異常信息:java.lang.OutOfMemoryError:Java heap spacess
java堆用于存儲對象實例,我們只要不斷的創(chuàng)建對象照卦,并且保證GC Roots到對象之間有可達(dá)路徑來避免垃圾回收機制來清除這些對象式矫,就會在對象到達(dá)最大堆容量限制后產(chǎn)生內(nèi)存溢出異常。
出現(xiàn)這種異常役耕,一般手段通過內(nèi)存影響分析工具(如Eclipse Memory Analyzer)對dump出來的堆轉(zhuǎn)存快照進(jìn)行分析采转,重點是確認(rèn)內(nèi)存中的對象是否必要,先分清是因為內(nèi)存泄漏(Memory Leak : 內(nèi)存泄漏也稱作"存儲滲漏"瞬痘,用[動態(tài)存儲]分配函數(shù)動態(tài)開辟的空間故慈,在使用完畢后未釋放,結(jié)果導(dǎo)致一直占據(jù)該內(nèi)存單元图云。直到程序結(jié)束惯悠。(其實說白了就是該內(nèi)存空間使用完畢之后未回收)即所謂內(nèi)存泄漏邻邮。)還是內(nèi)存溢出(Memory Overflow)竣况。
如果是內(nèi)存泄漏,引用可進(jìn)一步通過工具查看泄漏對象到GC Roots的鏈筒严。于是就能找到泄露對象時是通過怎樣的途徑導(dǎo)致垃圾收集器無法自動回收丹泉。
如果不存在內(nèi)存泄漏,那就應(yīng)該檢查虛擬機的參數(shù)(-Xmx與-Xms)的設(shè)置是否適當(dāng)鸭蛙。
2.虛擬機棧和本地方法棧溢出
如果線程請求的棧深度大于虛擬機所允許的最大深度摹恨,將拋出StackOverflowError異常。
如果虛擬機無法申請到足夠的內(nèi)存空間娶视,則拋出OutOfMemeryError異常
這里需要注意當(dāng)棧的大小越大晒哄,可分配的線程就越小。
3肪获、運行時常量池溢出
異常信息:java.lang.OutOfMemoryError:PermGen space
如果要向運行時常量池中添加內(nèi)容寝凌,最簡單的做法是使用String.interm()這個Native方法。該方法的作用是:如果池中已經(jīng)包含了一個等于此String的字符串孝赫,則返回代表池中這個字符串的String對象较木,否則,將此String對象包含的字符串添加到常量池中青柄,并且返回此String對象的引用伐债。由于常量池分配在方法區(qū)內(nèi),我們可以通過-XX:PermSize和-XX:MaxPermSize限制方法區(qū)的大小致开,從而間接限制其中常量池的容量峰锁。
4、方法區(qū)溢出
方法區(qū)用于存放Class的相關(guān)信息双戳、如類名祖今、訪問修飾符、常量池、字段描述千诬、方法描述等耍目。
異常信息:java.lang.OutOfMemoryError:PermGen space
方法區(qū)溢出也是一種常見的內(nèi)存溢出異常,一個類如果要被垃圾收集器回收徐绑,判定條件是很苛刻的邪驮,經(jīng)常動態(tài)生成的大量的Class的應(yīng)用中,要特別注意這點傲茄。
SOF
程序中一旦出現(xiàn)死循環(huán)或者是大量的遞歸調(diào)用毅访,在不斷壓棧過程中,造成棧容量超過默認(rèn)大小而導(dǎo)致溢出盘榨。
棧溢出的原因:
- 遞歸調(diào)用
- 大量循環(huán)或死循環(huán)
- 全局變量是否過多
- 數(shù)組喻粹、List 、map數(shù)據(jù)過