1. 程式人生 > >Java三種記憶體分配策略:靜態的.棧式的和堆式的區別

Java三種記憶體分配策略:靜態的.棧式的和堆式的區別

我的想法是(應該說代表TIJ的觀點),如果沒有Garbage Collector(GC),上面的說法就是成立的.堆不象棧是連續的空間,沒有辦法指望堆本身的記憶體分配能夠象堆疊一樣擁有傳送帶般的速度,因為,誰會為你整理龐大的堆空間,讓你幾乎沒有延遲的從堆中獲取新的空間呢?這個時候,GC站出來解決問題.我們都知道GC用來清除記憶體垃圾,為堆騰出空間供程式使用,但GC同時也擔負了另外一個重要的任務,就是要讓Java中堆的記憶體分配和其他語言中堆疊的記憶體分配一樣快,因為速度的問題幾乎是眾口一詞的對Java的詬病.要達到這樣的目的,就必須使堆的分配也能夠做到象傳送帶一樣,不用自己操心去找空閒空間.這樣,
GC除了負責清除Garbage外,還要負責整理堆中的物件,把它們轉移到一個遠離Garbage的純淨空間中無間隔的排列起來,就象堆疊中一樣緊湊,這樣Heap Pointer就可以方便的指向傳送帶的起始位置,或者說一個未使用的空間,為下一個需要分配記憶體的物件"指引方向".因此可以這樣說,垃圾收集影響了物件的建立速度,聽起來很怪,對不對?那GC怎樣在堆中找到所有存活的物件呢?前面說了,在建立一個物件時,在堆中分配實際建立這個物件的記憶體,而在堆疊中分配一個指向這個堆物件的指標(引用),那麼只要在堆疊(也有可能在靜態儲存區)找到這個引用,就可以跟蹤到所有存活的物件.找到之後,GC將它們從一個堆的塊中移到另外一個堆的塊中,並將它們一個挨一個的排列起來,就象我們上面說的那樣,模擬出了一個棧的結構,但又不是先進後出的分配,而是可以任意分配的,在速度可以保證的情況下, Isn't it great?
但是,列寧同志說了,人的優點往往也是人的缺點,人的缺點往往也是人的優點(再暈~~).GC()的執行要佔用一個執行緒,這本身就是一個降低程式執行效能的缺陷,更何況這個執行緒還要在堆中把記憶體翻來覆去的折騰.不僅如此,如上面所說,堆中存活的物件被搬移了位置,那麼所有對這些物件的引用都要重新賦值.這些開銷都會導致效能的降低.此消彼長,GC()的優點帶來的效益是否蓋過了它的缺點導致的損失,我也沒有太多的體會,Bruce Eckel 是Java的支持者,王婆賣瓜,話不能全信.個人總的感覺是,Java還是很慢,它的發展還需要時間.