自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

面試重點:Java虛擬機常見問題詳解

新聞 后端
本文整理了有關Java虛擬機常見問題的總結,所列舉的技術點為面試重點。Java程序在運行時,需要在內存中的分配空間。為了提高運算效率,就對數據進行了不同空間的劃分,因為每一片區(qū)域都有特定的處理數據方式和內存管理方式。

 面試重點:Java虛擬機篇

一、Java引用的四種狀態(tài):

強引用

  用的最廣。我們平時寫代碼時,new一個Object存放在堆內存,然后用一個引用指向它,這就是強引用。

  如果一個對象具有強引用,那垃圾回收器絕不會回收它。當內存空間不足,Java虛擬機寧愿拋出OutOfMemoryError錯誤,使程序異常終止,也不會靠隨意回收具有強引用的對象來解決內存不足的問題。

軟引用

  如果一個對象只具有軟引用,則內存空間足夠時,垃圾回收器就不會回收它;如果內存空間不足了,就會回收這些對象的內存。(備注:如果內存不足,隨時有可能被回收。)

  只要垃圾回收器沒有回收它,該對象就可以被程序使用。軟引用可用來實現內存敏感的高速緩存。

弱引用

  弱引用與軟引用的區(qū)別在于:只具有弱引用的對象擁有更短暫的生命周期。

  每次執(zhí)行GC的時候,一旦發(fā)現了只具有弱引用的對象,不管當前內存空間足夠與否,都會回收它的內存。不過,由于垃圾回收器是一個優(yōu)先級很低的線程,因此不一定會很快發(fā)現那些只具有弱引用的對象。

虛引用

  “虛引用”顧名思義,就是形同虛設,與其他幾種引用都不同,虛引用并不會決定對象的生命周期。如果一個對象僅持有虛引用,那么它就和沒有任何引用一樣,在任何時候都可能被垃圾回收器回收。

  虛引用主要用來跟蹤對象被垃圾回收器回收的活動。


二、Java中的內存劃分:

Java程序在運行時,需要在內存中的分配空間。為了提高運算效率,就對數據進行了不同空間的劃分,因為每一片區(qū)域都有特定的處理數據方式和內存管理方式。

面試重點:Java虛擬機篇

1、程序計數器:(線程私有)

  • 每個線程擁有一個程序計數器,在線程創(chuàng)建時創(chuàng)建,

  • 指向下一條指令的地址

  • 執(zhí)行本地方法時,其值為undefined

2、虛擬機棧:(線程私有)

每個方法被調用的時候都會創(chuàng)建一個棧幀,用于存儲局部變量表、操作棧、動態(tài)鏈接、方法出口等信息。局部變量表存放的是:編譯期可知的基本數據類型、對象引用類型。

每個方法被調用直到執(zhí)行完成的過程,就對應著一個棧幀在虛擬機中從入棧到出棧的過程。

在Java虛擬機規(guī)范中,對這個區(qū)域規(guī)定了兩種異常情況:

  (1)如果線程請求的棧深度太深,超出了虛擬機所允許的深度,就會出現StackOverFlowError(比如***遞歸。因為每一層棧幀都占用一定空間,而 Xss 規(guī)定了棧的***空間,超出這個值就會報錯)

 ?。?)虛擬機??梢詣討B(tài)擴展,如果擴展到無法申請足夠的內存空間,會出現OOM

3、本地方法棧:

(1)本地方法棧與java虛擬機棧作用非常類似,其區(qū)別是:java虛擬機棧是為虛擬機執(zhí)行java方法服務的,而本地方法棧則為虛擬機執(zhí)使用到的Native方法服務。

(2)Java虛擬機沒有對本地方法棧的使用和數據結構做強制規(guī)定,Sun HotSpot虛擬機就把java虛擬機棧和本地方法棧合二為一。

(3)本地方法棧也會拋出StackOverFlowError和OutOfMemoryError。

4、堆:即堆內存(線程共享)

(1)堆是java虛擬機所管理的內存區(qū)域中***的一塊,java堆是被所有線程共享的內存區(qū)域,在java虛擬機啟動時創(chuàng)建,堆內存的唯一目的就是存放對象實例幾乎所有的對象實例都在堆內存分配。

(2)堆是GC管理的主要區(qū)域,從垃圾回收的角度看,由于現在的垃圾收集器都是采用的分代收集算法,因此java堆還可以初步細分為新生代和老年代。

(3)Java虛擬機規(guī)定,堆可以處于物理上不連續(xù)的內存空間中,只要邏輯上連續(xù)的即可。在實現上既可以是固定的,也可以是可動態(tài)擴展的。如果在堆內存沒有完成實例分配,并且堆大小也無法擴展,就會拋出OutOfMemoryError異常。

5、方法區(qū):(線程共享)

(1)用于存儲已被虛擬機加載的類信息、常量、靜態(tài)變量、即時編譯器編譯后的代碼等數據。

(2)Sun HotSpot虛擬機把方法區(qū)叫做***代(Permanent Generation),方法區(qū)中最終要的部分是運行時常量池。

三、Java對象在內存中的狀態(tài):

可達的/可觸及的:

  Java對象被創(chuàng)建后,如果被一個或多個變量引用,那就是可達的。即從根節(jié)點可以觸及到這個對象。

  其實就是從根節(jié)點掃描,只要這個對象在引用鏈中,那就是可觸及的。

可恢復的:

  Java對象不再被任何變量引用就進入了可恢復狀態(tài)。

  在回收該對象之前,該對象的finalize()方法進行資源清理。如果在finalize()方法中重新讓變量引用該對象,則該對象再次變?yōu)榭蛇_狀態(tài),否則該對象進入不可達狀態(tài)

不可達的:

  Java對象不被任何變量引用,且系統(tǒng)在調用對象的finalize()方法后依然沒有使該對象變成可達狀態(tài)(該對象依然沒有被變量引用),那么該對象將變成不可達狀態(tài)。

  當Java對象處于不可達狀態(tài)時,系統(tǒng)才會真正回收該對象所占有的資源。

四、判斷對象死亡的兩種常用算法:

1、引用計數算法:

給對象中添加一個引用計數器,每當有一個地方引用它時,計數器值就加1;當引用失效時,計數器值就減1;任何時刻計數器為0的對象就是不可能再被使用的。

但是,主流的java虛擬機并沒有選用引用計數算法來管理內存,其中最主要的原因是:它很難解決對象之間相互循環(huán)引用的問題。

2、根搜索算法:(jvm采用的算法)

設立若干種根對象,當任何一個根對象(GC Root)到某一個對象均不可達時,則認為這個對象是可以被回收的。

五、垃圾回收算法

1、標記-清除算法:

標記階段:先通過根節(jié)點,標記所有從根節(jié)點開始的可達對象。因此,未被標記的對象就是未被引用的垃圾對象;

清除階段:清除所有未被標記的對象。

2、復制算法:(新生代的GC)

  將原有的內存空間分為兩塊,每次只使用其中一塊,在垃圾回收時,將正在使用的內存中的存活對象復制到未使用的內存塊中,然后清除正在使用的內存塊中的所有對象。

3、標記-整理算法:(老年代的GC)

標記階段:先通過根節(jié)點,標記所有從根節(jié)點開始的可達對象。因此,未被標記的對象就是未被引用的垃圾對象

整理階段:將將所有的存活對象壓縮到內存的一端;之后,清理邊界外所有的空間

4、分代收集算法:

存活率低:少量對象存活,適合復制算法:在新生代中,每次GC時都發(fā)現有大批對象死去,只有少量存活(新生代中98%的對象都是“朝生夕死”),那就選用復制算法,只需要付出少量存活對象的復制成本就可以完成GC。

存活率高:大量對象存活,適合用標記-清理/標記-整理:在老年代中,因為對象存活率高、沒有額外空間對他進行分配擔保,就必須使用“標記-清理”/“標記-整理”算法進行GC。

六、垃圾收集器

1、Serial收集器:(串行收集器)

這個收集器是一個單線程的收集器,但它的單線程的意義并不僅僅說明它只會使用一個CPU或一條收集線程去完成垃圾收集工作,更重要的是在它進行垃圾收集時,必須暫停其他所有的工作線程(Stop-The-World:將用戶正常工作的線程全部暫停掉),直到它收集結束。

2、ParNew收集器:Serial收集器的多線程版本(使用多條線程進行GC)

  ParNew收集器是Serial收集器的多線程版本。

  它是運行在server模式下的***新生代收集器,除了Serial收集器外,目前只有它能與CMS收集器配合工作。CMS收集器是一個被認為具有劃時代意義的并發(fā)收集器,因此如果有一個垃圾收集器能和它一起搭配使用讓其更加***,那這個收集器必然也是一個不可或缺的部分了。

3、ParNew Scanvenge收集器

  類似ParNew,但更加關注吞吐量。目標是:達到一個可控制吞吐量的收集器。

停頓時間和吞吐量不可能同時調優(yōu)。我們一方買希望停頓時間少,另外一方面希望吞吐量高,其實這是矛盾的。因為:在GC的時候,垃圾回收的工作總量是不變的,如果將停頓時間減少,那頻率就會提高;既然頻率提高了,說明就會頻繁的進行GC,那吞吐量就會減少,性能就會降低。

吞吐量:CPU用于用戶代碼的時間/CPU總消耗時間的比值,即=運行用戶代碼的時間/(運行用戶代碼時間+垃圾收集時間)。比如,虛擬機總共運行了100分鐘,其中垃圾收集花掉1分鐘,那吞吐量就是99%。

4、G1收集器:

  是當今收集器發(fā)展的最前言成果之一,直到jdk1.7,sun公司才認為它達到了足夠成熟的商用程度。

5、CMS收集器:(老年代收集器)

CMS收集器(Concurrent Mark Sweep:并發(fā)標記清除)是一種以獲取最短回收停頓時間為目標的收集器。適合應用在互聯(lián)網站或者B/S系統(tǒng)的服務器上,這類應用尤其重視服務器的響應速度,希望系統(tǒng)停頓時間最短。

七、Java堆內存劃分:

Java 中的堆是 JVM 所管理的***的一塊內存空間,主要用于存放各種類的實例對象。

在 Java 中,堆被劃分成兩個不同的區(qū)域:年輕代 ( Young )、老年代 ( Tenured)。年輕代 ( Young ) 又被劃分為三個區(qū)域:Eden、From Survivor、To Survivor。 這樣劃分的目的是為了使 JVM 能夠更好的管理堆內存中的對象,包括內存的分配以及回收。

1.年輕代

年輕代用來存放新近創(chuàng)建的對象,尺寸隨堆大小的增大和減小而相應的變化,默認值是保持為堆大小的1/15,可以通過 -Xmn 參數設置年輕代為固定大小,也可以通過 -XX:NewRatio 來設置年輕代與年老代的大小比例,年青代的特點是對象更新速度快,在短時間內產生大量的“死亡對象”。

年輕代的特點是產生大量的死亡對象,并且要是產生連續(xù)可用的空間, 所以使用復制清除算法和并行收集器進行垃圾回收.對年輕代的垃圾回收稱作初級回收 (minor gc)。

2.老年代

Full GC 是發(fā)生在老年代的垃圾收集動作,所采用的是標記-清除算法。

現實的生活中,老年代的人通常會比新生代的人 “早死”。堆內存中的老年代(Old)不同于這個,老年代里面的對象幾乎個個都是在 Survivor 區(qū)域中熬過來的,它們是不會那么容易就 “死掉” 了的。因此,Full GC 發(fā)生的次數不會有 Minor GC 那么頻繁,并且做一次 Full GC 要比進行一次 Minor GC 的時間更長。 另外,標記-清除算法收集垃圾的時候會產生許多的內存碎片 ( 即不連續(xù)的內存空間 ),此后需要為較大的對象分配內存空間時,若無法找到足夠的連續(xù)的內存空間,就會提前觸發(fā)一次 GC 的收集動作。

3.***代

***代是Hotspot虛擬機特有的概念,是方法區(qū)的一種實現,別的JVM都沒有這個東西。在Java 8中,***代被徹底移除,取而代之的是另一塊與堆不相連的本地內存——元空間。

***代或者“Perm Gen”包含了JVM需要的應用元數據,這些元數據描述了在應用里使用的類和方法。注意,***代不是Java堆內存的一部分。***代存放JVM運行時使用的類。***代同樣包含了Java SE庫的類和方法。***代的對象在full GC時進行垃圾收集。

八、類加載機制:

面試重點:Java虛擬機篇

虛擬機把描述類的數據從Class文件加載到內存,并對數據進行校驗、轉換解析和初始化,最終形成可以被虛擬機直接使用的Java類型,這就是虛擬機的類加載機制。

對應常見筆試題

注意:子類初始化問題:滿足主動調用,即父類訪問子類中的靜態(tài)變量、方法,子類才會初始化;否則僅父類初始化。

面試重點:Java虛擬機篇

面試重點:Java虛擬機篇

面試重點:Java虛擬機篇

面試重點:Java虛擬機篇

注意:訪問類或接口的靜態(tài)變量(特例:如果是用static final修飾的常量,那就不會對類進行顯式初始化。static final 修改的變量則會做顯式初始化)

面試重點:Java虛擬機篇

面試重點:Java虛擬機篇

面試重點:Java虛擬機篇

上面的運行效果顯示,由于c是final static修飾的靜態(tài)常量,所以根本就沒有調用靜態(tài)代碼塊里面的內容,也就是說,沒有對這個類進行顯式初始化。

責任編輯:張燕妮 來源: 頭條科技
相關推薦

2009-09-25 15:46:46

虛擬機軟件

2009-11-02 17:25:04

ADSL常見問題

2009-12-31 09:58:51

Ubuntu常見問題

2020-05-08 16:55:48

Java虛擬機JVM

2011-04-01 13:55:24

Java

2009-10-16 13:24:53

2011-08-08 09:27:49

虛擬化虛擬機虛擬映像

2011-08-08 09:17:27

虛擬化虛擬機虛擬映像

2018-02-24 12:54:51

Java虛擬機面試

2009-02-04 18:20:42

服務器虛擬化VMware

2009-12-11 14:00:09

VMware虛擬機

2012-02-06 10:37:07

Java

2009-08-07 11:46:57

JAVA虛擬機安裝設置

2015-08-20 11:01:22

Java虛擬機GC算法種類

2024-03-29 11:42:21

Java虛擬機

2018-09-11 14:47:51

面試Java虛擬機

2024-03-26 07:30:07

Java虛擬機源文件

2011-04-29 15:47:41

一體機

2009-10-19 11:33:22

數據中心綜合布線

2009-06-04 16:27:39

Java虛擬機JVMGC
點贊
收藏

51CTO技術棧公眾號