天天看點

五分鐘學Java:如何學習Java面試必考的JVM虛拟機

原創聲明

本文作者:黃小斜

轉載請務必在文章開頭注明出處和作者。

本文思維導圖

為什麼要學習JVM虛拟機

最近的你有沒有參加Java面試呢?你有沒有發現,Java面試中總是愛考一類問題,那就是JVM虛拟機,為什麼面試官這麼愛考察JVM的問題呢,這是因為,所有的Java程式本質上都是運作在JVM之上的,沒有JVM虛拟機,也就沒有Java語言的執行環境,隻有掌握了JVM虛拟機的相關知識,你才能說你懂Java,否則就像一個隻會玩手機的人說自己壓根不懂安卓作業系統一樣。

根據百度百科的介紹,JVM是Java Virtual Machine(Java虛拟機)的縮寫,JVM是一種用于計算裝置的規範,它是一個虛構出來的計算機,是通過在實際的計算機上仿真模拟各種計算機功能來實作的。引入Java語言虛拟機後,Java語言在不同平台上運作時不需要重新編譯。Java語言使用Java虛拟機屏蔽了與具體平台相關的資訊,使得Java語言編譯程式隻需生成在Java虛拟機上運作的目标代碼(位元組碼),就可以在多種平台上不加修改地運作。

就是因為有JVM的存在,Java才能夠擁有跨平台運作的能力,一次編譯,到處運作,反觀C++這類語言,需要到處編譯才能運作,因為它本身是和作業系統強關聯的一門語言,也沒有虛拟機的概念。

當然,因為有了JVM虛拟機的存在,Java語言的複雜度也大大降低,其所付出的代價就是運作速度有所下降,離開JVM虛拟機談Java是沒有意義的,學好JVM是學好一切Java技術的前提。

如何學習JVM虛拟機

JVM虛拟機就在我們的身邊

第一次聽說JVM虛拟機這個東西,還是在一道面試題中,那時候我完全不知道這是個啥玩意啊,後來我買了一本号稱JVM聖經的書《深入了解JVM虛拟機》才有幸知道,原來JVM虛拟機就運作在我們的電腦中。

作為一個Java開發者,入門三件套可能就是IDE、JDK和JRE了,其實JDK就包含了JRE,而JRE(Java運作環境)也就包含了JVM虛拟機。當我們使用javac或者使用ide進行Java程式的編譯或者執行時,其實就是把java代碼變異成class位元組碼,然後扔到JVM執行。

此時我們的任務管理器裡會有一個程序叫做java,這個程序就可以了解為JVM程式,而這個程序裡還有很多子線程,分别負責執行代碼,垃圾回收等等。

很多時候我們壓根不知道JVM虛拟機是個啥,自然也不能很好地學習它,一旦我們了解了它的本質,後面的東西學習起來也就不會那麼痛苦了。

初探JVM面試題

有很多程式員第一次聽說JVM可能是在面試的時候,關于JVM的面試題其實也不少,這裡舉例一些比較熱門的面試題型,比如“JVM的堆和棧有什麼差別”、“JVM的垃圾回收算法有哪些”、“JVM的記憶體模型是什麼樣的”等等,這類題目算是比較基礎的了。

這類題目,一般通過刷刷面經,也能夠回答上來一些,畢竟面試官懂得也不一定比你多,是以一些面試官可能也不會深挖下去。不過如果是一些對技術考察得比較有深度的公司就不一定了,很多以Java技術棧為主的公司,特别是電商類公司,對于JVM的考察還是比較有深度的,除了阿裡和美團,還有京東、唯品會、有贊、拼多多等公司。

是以,我們不妨也來看看進階版的JVM面試題長什麼樣。首先,進階版的題目主要考察深度,像是JVM的記憶體模型,一定會讓你講清楚每個區域是做什麼的,并且會讓實際的場景來問你,比如字元串變量放在哪個區域,類的中繼資料放在哪個區域,局部變量和全局變量又分别放在哪個區域。如果你對記憶體模型隻是一知半解,一下子就會被面試官給識破了。

進階版的JVM面試還喜歡考察細節,比如JVM的垃圾回收算法,停止複制,标記清除,需要你把過程講清楚,各自的優劣講清楚。如果這類問題對你也夠不成威脅,那不妨再看看JVM垃圾回收的其他題型,“年輕代的GC是如何進行的,請講解詳細過程”很多面試者可能會簡單地講一下年輕代的回收方法。

你可能會簡單地回答:“使用停止複制的方法來完成的”實際上,其實,這裡面能講的細節有很多,首先,年輕代分為eden區和survivor區,survivor區還分為from和to區,eden區存活的對象會被放到from區,而在下一次young gc後,from區和to區會交換位置,對象也會跟着搬移,進而該對象的年齡加一,當對象的年齡超過門檻值時,對象就會進入老年代。

看似簡單的問題居然可以答出這麼多門道,這也是我在經曆很多次面試之後才總結出來的經驗。

JVM聖經《深入了解JVM虛拟機》

Java書籍千千萬,但是真正能夠講清楚JVM虛拟機的書可能也隻有這一本了。網上的大部分關于JVM的部落格基本都是借鑒或者是參考本書的内容。

那麼這本書到底講了哪些些JVM的内容了,不妨和我一起來拆解一下。

第一部分,這本書講了Java這門語言的曆史,以及它為什麼要運作在JVM上,這一點很重要,要不然開發者也會很奇怪,為什麼好好的程式設計語言要運作在虛拟機上呢。

第二部分,本書開始介紹JVM的核心概念,那就是記憶體模型,JVM是如何管理計算機的記憶體的,又是如何劃分這些區域的,畢竟Java裡的類型和變量那麼多,确實不好管理。

第三部分,是這本書比較難的一部分,它開始介紹Java代碼的運作原理,那就是要先把java代碼編譯成位元組碼,然後才能在JVM上執行,而Java代碼又是由一個個類組成的,是以文章要介紹JVM虛拟機是如何加載這些類的,這裡面有很多新穎的概念,值得我們去探索。

第四部分,程式編譯和代碼優化,這部分内容其實比較冷門,但實際上是很複雜的,這裡面提到了很多JVM對于程式執行的優化,包括編譯期的優化和運作期的優化,優化的目的是讓Java程式更高效地運作,了解了這部分内容之後,你一定會對JVM虛拟機的設計産生崇敬之情。

第五部分,主要介紹了JVM對Java多線程的支援,Java中的多線程自然也是基于JVM進行設計和實作的,其中就涉及到了我們常用的鎖,這裡主要介紹的是synchronized,它的本質是互斥鎖,但是随着JVM對于重量級鎖synchronized的優化,它也逐漸開始支援輕量級鎖和偏向鎖。

可以說,本書全程都是精華,基本上都是重點,考試會考,當然其中也有一些内容比較冷門,不怎麼受面試官待見。但是這本書基本上把JVM裡我們需要掌握的知識都講清楚了,對于JVM的理論學習,這一本書足矣。

JVM調優實戰

講完了理論,終于到了實戰的部分。

JVM知識整體看來是一個偏理論的知識子產品,似乎能實踐的東西不多,但實際上,JVM方面能實踐的東西可不少,比如JVM調優,JVM的GC分析以及記憶體分析,都是面試官很喜歡考察的實踐能力。

接下來的部分,我們就來講講JVM實戰的内容。

在一些進階Java面試中,關于JVM的問題可能就會涉及到JVM調優和實踐上了,比如你有沒有遇到過OOM或者記憶體洩漏,你是怎麼發現它們的,又或者,GC過于頻繁,我們應該如何進行排查。

總之,這類問題都是立足于實踐,考察的就是候選人的實踐經驗,這對于平時一直CRUD,連伺服器都沒怎麼碰過的朋友來說,确實是一個不小的挑戰。

那咋辦呢,其實辦法也不是沒有,畢竟我就是一個沒有JVM實踐經驗的小白,之前我對于這方面的複習主要是通過幾個方法。

找一些比較知名的JVM調優工具,試用一下,比如Jprofile,還有JDK自帶的jmap jstack等等。把這些工具都拿來用于自己的程式測試,寫幾個oom或者是記憶體洩漏的程式,看看工具裡都會出現什麼情況,這就是其中一種不錯的學習方法。

但是有人會說,很多面試題都是要有高并或者高負載的場景,平時自己的代碼根本不會出現這種問題,那怎麼辦呢,其實也有辦法,網上對于這類調優面試題其實也有很多分享,針對某一種場景如何調優,操作步驟應該是怎樣的,其實都能從别人的文章中找到一些答案,這樣,即使你平時工作沒有這類實踐,也可以通過學習JVM調優實戰的文章來進行複習,其實道理都是一樣的。

推薦資源

書籍

《深入了解JVM虛拟機》

視訊

我整理了一些JVM方面的學習視訊,分享給大家,其實這方面的視訊資源并不多,畢竟大多數視訊還是講項目或者基礎為主,能把JVM虛拟機講透講好的人确實不多。

部落格

Java技術倉庫《Java程式員複習指南》

https://github.com/h2pl/Java-Tutorial

整合全網優質Java學習内容,幫助你從基礎到進階系統化複習Java

面試指南

全網最熱的Java面試指南,共200多頁,非常實用,不管是用于複習還是準備面試都是不錯的。

總結

關于如何學習JVM虛拟機,并且搞定相關面試題,我們今天就講到這裡了,如果還有什麼疑問也可以到我公衆号【程式員黃小斜】裡找我探讨,後續會有更多的文章推出,包括如何系統性地學習JavaWeb,敬請期待。

對了,你想問我文章裡提到的書籍和視訊去哪找?我已經給你準備好了

文中提到的資源都可以免費領取,在我的公衆号【程式員黃小斜】回複“Java并發程式設計”即可免費領取對應的資源。

寫在最後

如果覺得本文對你有幫助的話,請你也不要吝啬你的“好看”哈,轉發朋友圈就是對我最大的支援啦,你們的支援是對我最大的鼓勵。

對本系列文章有什麼建議和意見,也歡迎留言告訴我,期待你的回饋。