
摘要:java是當前比較火的一門編程語言,由于java的跨平臺性使得java的應用在越來越多的方面得以體現,在java大行其道的背后有著一個默默無聞的工作角色,這個角色就是java虛擬機——JVM,在本文中對JVM的運行過程做了一些研究,并綜合闡述了JVM的運行部件和運行機制。
關鍵詞:JVM java虛擬機 跨平臺 面向對象編程
Java因為其良好的跨平臺性,得到越來越多程序員的喜歡,同時隨著智能化家居的日益普及,java已經從開發的神壇走向平常百姓身邊。無時無刻我們的身邊都有java設備的運行,網絡電視中的android平臺,運行在其上的各種APP都是java運行的結果,車載系統已經從原先最早的嵌入式形式走向現在更具體的獨立系統階段,裝上android系統,各種應用便可以進行拓展,不得不說,java已經是我們親密的伙伴和朋友。但是在此不得不說,一個非常重要的幕后英雄,JVM(java虛擬機Java Virtual Machine)。
總所周知,操作系統封裝了底層的硬件設備,為人們使用計算機設備提供了人性化接口,為編程提供了各種API調用接口,但是各種操作系統在給人們提供便利的同時,又因為彼此的不同,給開發應用系統帶來一定的阻礙,因為針對一種系統的應用要運行在另外一個系統上的話,必然要在此開發針對另外系統的應用,增加了人們的開發工作量。為了解決這一問題,Sun公司開發了java語言,當然其初衷并非如此,但是確實也達到了這樣的目的,至于其初衷在此不做討論。Java語言使用Java虛擬機屏蔽了與具體平臺相關的信息,使得Java語言編譯程序只需生成在Java虛擬機上運行的目標代碼(字節碼),就可以在多種平臺上不加修改地運行。JVM是java的核心和基礎,它是建立在java編譯器和操作系統平臺之間的虛擬電腦,或者狹義的理解為虛擬處理器,其運行基于下層操作系統和硬件平臺通過軟件來實現的抽象的計算機。java編譯器只需根據JVM編譯即可,程序員可以根據統一的標準去編寫程序,讓更做的重點放在工作流和業務流上。編譯器只需生成JVM能理解的代碼或者字節碼文件即可,JRE(java運行環境)將每一條指令翻譯成不同平臺的機器碼,保證其在不同平臺上的運行。
一個程序從源代碼到運行的執行過程如下:
1.編寫java源文件。
2.Javac編譯器將源文件編譯成class文件。
3.加載.class文件。
然后虛擬機采用如下圖所示的處理過程執行程序:
下面對JVM的運行組成做個說明:
1.JVM指令系統
JVM是對底層系統的抽象,同計算機指令系統一樣,JVM提供指令系統,其指令也是由操作碼和操作數兩部分構成,JVM操作碼是8位二進制數,所以JVM提供醉倒256種指令,已經使用160多種。
2.JVM寄存器
在普通的操作系統中,CPU包含一定的寄存器,JVM也設置了幾種常用的寄存器,PC程序計數器,OPTOP操作數棧頂指針,FRAM當前執行環境指針,VARS指向當前執行環境第一個局部變量的指針。其中所有 寄存器都是32位,PC記錄程序的執行,其他幾個寄存器記錄指向java棧區的指針。
其中,PC程序計數器可以理解為當前線程所執行的字節碼行號指示器,在JVM概念模型中,字節碼解釋器通過改變計數器的值來選取下一條需要執行的字節碼指令,分支、循環、跳轉、異常處理等都依賴于程序計數器。
3.堆棧結構以及存儲區
JVM主要用棧來存儲信息,當JVM得到.class的字節碼后便為該代碼中一個類的每個方法創建一個包含局部變量、執行環境、操作數的棧框架。,VARS寄存器指向局部變量中第一個變量的位置。操作數棧主要用于保存運算所需要的操作數以及運算的結果,執行的時候從棧頂彈出操作數進行運算,最后將運算結果壓人棧頂。解釋器具體承擔實例空間的分配工作,解釋器為實例分配完存儲空間后就可以記錄該實例所占用的內存區域的使用,一旦對象使用完畢就將其回收到堆中。也就是使用NEW語句構造出來的對象最終要存在堆上,如果不再使用則由垃圾回收機制回收,即堆是java垃圾收集器管理的主要區域,所以很多時候它稱為GC區。為了存放類名稱、方法和字段名稱以及串常量,這些元素存放在JVM中的常量緩沖池,Java方法的字節碼則存放在方法區。
4.垃圾回收機制
使用過C++編程的人一定會為C++中內存泄漏而苦惱,因為C++運行環境中,對象所占的內存在程序結束后不會主動釋放,其釋放必須通過程序員調用代碼釋放,而在Java中有完善的垃圾回收機制,在對象引用沒有指向原先分配給某個對象的內存時,便忍者這塊內存便成是垃圾。JVM的一個系統級線程會自動釋放該內存塊。垃圾回收意味著程序不再需要的對象是“無用信息”,這些信息將被丟棄。當一個對象不再被引用的時候,內存回收它占領的空間,以便空間被后來的新對象使用。事實上,除了釋放沒用的對象,垃圾回收也可以清除內存記錄碎片。由于創建對象和垃圾回收器釋放丟棄對象所占的內存空間,內存會出現碎片。碎片是分配給對象的內存塊之間的空閑內存洞。碎片整理將所占用的堆內存移到堆的一端,JVM將整理出的內存分配給新的對象。垃圾回收能自動釋放內存空間,減輕編程的負擔。這使Java 虛擬機具有一些優點。首先,它能使編程效率提高。在沒有垃圾回收機制的時候,可能要花許多時間來解決一個難懂的存儲器問題。在用Java語言編程的時候,靠垃圾回收機制可大大縮短時間。其次是它保護程序的完整性,垃圾回收是Java語言安全性策略的一個重要部份。
經常有人說java的執行效率低,畢竟因為java是在底層的基礎之上做了一層封裝,其實現在經過JVM的優化,只要站在底層運行的角度去編寫代碼、優化代碼和其他編譯性程序語言相比,這種差距也越來越小,相比于JVM帶來的極大便利,這點差距又算得了什么呢。
(作者簡介:張衛,碩士研究生學歷,計算機科學與技術專業,銅仁幼兒師范高等專科學校講師,研究方向有:網格計算,計算機軟件與程序設計,多年從事一線教育工作和知名大學計算機實訓培訓工作。)