你們好,我是片頭專欄《從零開始帶你成爲JVM實戰高手》的做者,外號救火隊隊長,目前在阿里任職。java
這個專欄已經寫做一週了,也在好友石杉老哥公衆號這裏宣傳霸屏一週了,實在是感謝老哥們兒的大力推薦,有空來杭州必定請你喝兩杯^_^web
好了,言歸正傳,從第一週讀者的反響來講,總體很好,由於定位是從零開始,我用了大量的手繪彩圖進行講解,這點深得你們贊同。windows
不過,也有很多「老鳥」同窗但願快一些,儘快到達後面的精華部分:案例實戰。不過我仍是想提一句,由於照顧到不少JVM基礎薄弱甚至沒有基礎的同窗,因此仍是會穩紮穩打,但願這些有基礎的同窗,權當複習一遍吧!tomcat
另外,第一週的文章,你們的互動也很活躍。看到這些我很是欣慰,若是光是我寫,你不思考,那效果會大打折扣。安全
下面,我整理了第一週全部同窗問題中最典型的30個問題,並給出瞭解答,你們能夠仔細看看,認真思考,看是否是你也對這些問題曾經有過疑惑?微信
問題多線程
方法走完,引用消失,堆內存還未必消失。好多人在作報表導出的時候,就會在for循環裏不斷的建立對象,很容易形成堆溢出,請問這種大文件導出怎麼破?併發
解答 jvm
建議不要在for裏建立對象,能夠在外面搞一個對象,for循環裏對一個對象修改數據便可工具
問題
1.Java支持多線程,每一個線程有本身的Java虛擬機棧和本地方法棧,是這樣嗎?
2.新建的實例在堆內存,實例變量也是在堆內存? 是這樣嗎?
解答
一、2兩點均理解正確
問題
您好,我不太看懂入棧和出棧有什麼意義,能夠給我解釋一下嗎?謝謝!
解答
入棧的時候,就是你執行一個方法的時候,爲這個方法建立一個棧幀入棧
出棧,就是你的方法執行完畢了,就會出棧,其實這個不用急,明天的文章會有詳細的圖解,你會看明白的。
問題
若是是父類子類的狀況是下面哪一種呢? 加載父類->加載子類->初始化父類->初始化子類, 加載父類->初始化父類->加載子類->初始化子類
解答
不是的,加載父類就是父類,除非用到子類纔會加載子類;可是加載子類要初始化以前,必須先加載父類,初始化父類
問題
類加載器有三層,若是在第二層的類加載器能夠加載這些類的話,就沒有必要往上去找他的父類加載嗎?
既然說類只有用到的時候才加載到內存中,那麼new對象的時候確定用到,可是是否是先經歷過類的全部過程纔將類實例化?
解答
沒錯,必須先加載類,再實例化對象
問題
第一課內容比較詳細的講解了java程序的執行過程,可是感受提出的問題並不能在文章中找到答案,也許是一個課後須要本身找尋答案的提問?仍是但願能夠有一個比較全面的回答的
解答
提出的問題是給你們的思考題,次日會給出簡單的解釋,可是其實理解了文章的內容,徹底能夠本身找資料去理解,這是一個小做業,是一個思考的過程
問題
Object Header(4字節) + Class Pointer(4字節)+ Fields(看存放類型),可是jvm內存佔用是8的倍數,因此結果要向上取整到8的倍數
解答
很好,就是這樣
問題
若是我有一個靜態的成員變量int,那我多線程更改是否會有線程安全問題,爲何?
解答
靜態成員變量,他在內存裏,只有一份,就是屬於類的。你多個線程併發修改,必定會有併發問題,可能致使數據出錯。
問題
類加載是按需加載,能夠一次性加載所有的類嗎?
解答
若是是默認的類加載機制,那麼是你的代碼運行過程當中,遇到什麼類加載什麼類。若是你要本身加載類,那麼須要寫本身的類加載器
問題
爲何必需要一級一級類加載器的往上找,直接從頂層類加載器開始找不就好了嗎?
解答
其實關於這個問題,不用過於糾結,每一層類加載器對某個類的加載,上推給父類加載器,到頂層類加載器,若是發現本身加載不到,再下推回子類加載器來加載,這樣能夠保證絕對不會重複加載某個類。
至於爲何不直接從頂層類加載器開始找,那是由於類加載器自己就是作的父子關係模型
你想一下Java代碼實現,他最底下的子類加載器,只能經過本身引用的父類加載器去找。若是直接找頂層類加載器,不合適的,那麼頂層類加載器不就必須硬編碼規定了嗎?
這就是一個代碼設計思想,保證代碼的可擴展性。
問題
是在執行new replicamanager()這行代碼的時候加載replicamanger類嗎?仍是說加載cafka的時候就同時加載了呢?
解答
執行new ReplicaManager的時候加載類
問題
仍是沒有明白 jvm和平時運行在機器上的系統之間是什麼關係呢
解答
其實很簡單,你運行在機器上的系統,其實就是一個JVM進程,JVM進程會執行你係統裏寫好的那些代碼
問題
解答
問題
雙親委派能夠解決類重複加載的問題。按照文章中介紹每一個類加載器有不一樣的類加載路徑,這些類加載路徑是否可能重疊?
解答
不一樣類加載器的路徑,通常是不會重疊的
問題
自定義的類加載器自己是由系統加載器加載的,也就是說其自己是沒有加密的,那麼我拿到該類反編譯就能夠看到若是解密class文件了,請問老師是這樣麼?
解答
是的,因此說對class文件須要作特殊混淆處理,有商用的產品能夠用
問題
做爲一個web容器,既要解決跨應用公共共享問題也要解決獨立應用獨立問題。tomcat必須支持多層級的自定義類加載器
解答
很好的推測,明天會給出答案
問題
用戶使用類的時候應該是但願類已經準備好了一些數據,我猜測jvm設計者設計先執行static代碼塊的機制,是但願開發者在這裏把使用類以前須要準備的工做在這裏準備好
解答
問題
其實初始化時機就是對類的主動使用:調用靜態方法時對類的主動使用的一種場景,main方法本質上是個static方法,沒有調用的main方法和沒有調用的static方法沒區別!
有一個問題,包含main方法的類會優先加載,若是一個項目中有多個類中都有main方法,都會加載麼?
解答
不會的,你啓動一個jar包,須要指定某個main主類,優先就是加載他
問題
tomcat自己是java程序,那麼tomcat的實現程序的class是由應用類加載器加載的,用戶本身的java程序war包,放入tomcat的程序的classpath中
這樣用戶的程序和tomcat的程序都是由應用類加載器加載了,也就是處於一個jvm中了
解答
很是好的回覆,明天文章會給出答案
問題
有一個問題,包含main方法的類會優先加載,若是一個項目中有多個類中都有main方法,都會加載麼?
解答
你啓動一個jar包的時候,會指定是走哪一個main方法所在的類,是惟一的
問題
解答
問題
老師好請問類加載雙親委派機制 爲何要先找父加載 而不是本身找?這種設計的好處是?
解答
好處就在於,每一個層級的類加載器各司其職,並且不會重複加載一個類。
好比你代碼裏用兩個不一樣層級的類加載器,都去嘗試加載了某個類,若是有雙親委派機制,那麼都會先找父類加載器去加載,若是加載到了,那麼之後就只會是他去加載這個類。
不然若是沒有雙親委派機制,那麼豈不是兩個不一樣層級的類加載器能夠加載同一個類,形成類的重複加載!
問題
自定義類加載器如何實現?
解答
本身寫一個類,繼承ClassLoader類,重寫類加載的方法,而後在代碼裏面能夠用本身的類加載器去針對某個路徑下的類加載到內存裏來
問題
看到一個詞:動態部署,那麼是否也有對應的靜態部署?如何解釋呢?(謝老師回答)
解答
假設一個背景在Tomcat部署系統的話,那麼動態部署,也成爲熱部署
就是直接系統放入Tomcat對應目錄,他自動就從新加載你最新的代碼給你熱部署了,不須要對Tomcat進行停機再重啓;
反之,則是先中止Tomcat,而後部署最新代碼到Tomcat對應目錄裏,而後重啓Tomcat
問題
-XX:+TraceClassLoading 能夠看加載了哪些類,動手實驗了一下,jre\lib\rt.jar下的類所有加載了,其餘都是用到時候加載。
解答
沒錯,明天更新的第三篇文章裏,會講解類加載機制,rt.jar這屬於核心類庫,屬於支撐咱們Java系統運行的底層類庫,因此他必定會被加載
咱們本身寫的代碼,通常是你代碼運行使用到了哪一個類,就會去加載哪一個類
問題
老師,類加載器是把jar包裏的全部類一次性所有加載進去嗎?
解答
不是的,首先加載包含main方法的主類,接着是運行你寫的代碼的時候,遇到你用了什麼類,再加載什麼類
問題
經過代碼混淆機制,加大反編譯以後的可讀性!或者是否能夠基於二進制加密呢,學生沒用過!
解答
其實如今對於這個通常都是用商業產品的,有不少第三方公司提供加密產品,能夠百度一下,class文件加密,就能夠看到,直接用他們的產品便可
問題
Class源文件的保護,能夠採用代碼混淆技術,方式有不少,如回答區中老師提到的商用加密軟件
解答
很是好,就是這樣
問題
看文中內容,是會加載兩次字節碼嗎,第一次加載進jvm,而後程序執行的時候再加載。有點不解!
解答
你好,不是加載兩次,是JVM先把「.class」字節碼文件中的類加載到內存裏,而後執行的時候,就直接使用加載好的類極客,不會重複加載
問題
class文件經過工具能夠反編譯的,請問有沒有方法對class文件進行加密又不影響它的執行。windows桌面程序裏通常都是打包成dll文件,java中有沒有比較好的方式?
解答
能夠的,好比jvmti小工具就能夠實現class文件的加密
另外其實爲了保護源代碼安全,有不少商業公司推出了專業級別的class加密產品,能夠付費使用。
解密的話通常能夠基於自定義的類加載器來實現,在加載類的時候把class給解密,這樣就能夠保護本身的源代碼安全了。
最後,附上兩張Tomcat類加載若是按委派模型的加載流程和實際實現的流程(專欄讀者所畫)
這些,就是本週展現的典型問題了。你都理解了嗎?
專欄剛更新一週,收穫了很多同窗的好評,這是對我寫做付出的最好回報。在此繼續霸佔朋友的公號,給本身打個小廣告,厚着臉皮貼出截圖,感謝你們支持!
END
推薦一個專欄:
《從零開始帶你成爲JVM實戰高手》
做者是我多年好友,之前團隊的左膀右臂
一塊兒經歷過各類大型複雜系統上線的血雨腥風
現任阿里資深技術專家,對JVM有豐富的生產實踐經驗
專欄目錄參見文末,能夠掃下方海報進行試讀
經過上面海報購買,再返你24元
領取方式:加微信號:Giotto1245,暗號:返現