我在這個主題上閱讀過的很多書籍和文章,以及我用'不安全'寫的一個小程序,都表明Java中的一維數組在內存中始終是連續的。那麼它是由JLS規定還是實施慣例?這個問題被要求確認這個指示。Java:一維數組是否總是在內存中連續?
回答
沒有,JVM規範沒有任何這樣的保證: http://docs.oracle.com/javase/specs/jvms/se5.0/html/Concepts.doc.html#16446
在實踐中它可能是這樣,但你也沒有這個字大小的保證。
不安全是不是一個標準的Java類,所以如果你的程序使用此,那麼它是不可移植的反正...
由於在Java中沒有真正的與內存地址交互的方式,所以在規範中也沒有定義內存中對象佈局的外觀。
請注意,使用Unsafe
幾乎會自動意味着您正在漫遊規範領域之外。這就是說,我敢說大多數JVM實現做實際上使用線性佈局(一維)數組。
鑑於許多JVM的有一個要求,即堆是連續在內存中,我認爲它不太可能他們會在內存中的不同位置放置一個1d的基元數組。
Object []引用的對象不可能在內存中連續存在,即使它們是可以在沒有警告的情況下重新排列。
注意:使用不安全,您可以讀取數組中的引用作爲int
值,以查看GC之前和之後的內容。某些JVM使用64位引用,這需要很長的時間,但大多數情況下使用32位bti引用(即使是64位JVM)。
我想用The Java Language Specification, Java SE 8 Edition (JLS)和The Java Virtual Machine Specification, Java SE 8 Edition (JVMS)對此的看法來刷新此問題。
我們必須的選擇,這個問題的答案:
- 在JVM實現強加什麼約束。這是最可靠的方法,因爲任何規範的實現固有地假定爲「允許的所有不被禁止的」原理。
- 最令JVM實現合理的建議
我會指出來規範約束。
如果我們看一下第10章陣列的 JLS(以及相關的陣列JLS和JVMS任何其他章節),我們找不到強加給數組的內存佈局約束任何提及。 因此,它肯定意味着該陣列可能不是連續的。
此外,JLS說,陣列是對象:
第10章陣列。
在Java編程語言中,數組是 對象(第4.3.1節),被動態地創建,並且可以被分配給Object類型的 變量(§4.3.2)。類Object中的所有方法可能是在數組上調用 。
...4.3.1。對象。
一個目的是類實例或陣列。 (和陣列是Object)
並在同一時間JVMS說,對象和數組存儲在堆上:
2.5.3。堆
Java虛擬機具有在所有Java虛擬機線程中共享的堆。 堆是運行時數據區域 ,從中分配所有類實例和數組的內存。
但JVMS不會強迫堆內存是連續的:
2.5.3。堆
... 堆的內存不需要連續。
由於所有數組存儲在堆和堆可能是不連續的,它遵循陣列也可能是不連續的。
- 1. argv數組的元素在內存中是否總是連續的?
- 2. std :: array中的內存是否連續?
- 3. mmap是否連續分配堆內存?
- 4. 新[]是否連續分配內存?
- 5. pkt_data是否連續佔用內存?
- 6. 二維數組的連續內存分配---釋放內存
- 7. 數組是否連續存儲在所有語言中?
- 8. 如何找到一個子數組是否在Java中的二維數組內有特定的總和?
- 9. 爲整數的二維數組分配內存但它應該是連續的
- 10. 連續的'新'操作符是否連續分配內存?
- 11. 如何連續(連貫地)在C++內存中存儲三維數組?
- 12. Java 2維整數數組檢查是否存在
- 13. 在C++中,矢量是否佔用連續的內存插槽?
- 14. 激活記錄是否在內存中連續?
- 15. Android內存分配器 - 內存是否需要連續?
- 16. 確定元組中是否存在連續序列
- 17. 如何檢查輸入數組是否連續或不連續?
- 18. Typescript:搜索一個數組(行)是否存在於一個二維數組中
- 19. knockoutjs - 檢查數組中是否存在項總是返回true
- 20. 是否構造函數總是需要一個內存分配
- 21. 動態二維數組非連續內存C++
- 22. 簡單的函數來檢查一個數組是否連續
- 23. 是否可以在一個數組中存儲多個多維數組?
- 24. 是否存在與下劃線(_)連續相反的內容?
- 25. 排序二維數組,數字應該是連續
- 26. 檢查數值是否存在於多維數組中
- 27. NSData/Data存儲是否連續?
- 28. 在Windows上,內存中的數據是否可以跨虛擬內存頁連續存在?
- 29. 檢查是否在一個PHP存在數組值多維數組
- 30. 什麼是連續內存塊?
同意,但陣列本身將是連續的,對不對?這樣的事情:1000-> aa,1001-> bb,1002-> cd等 – shrini1000 2012-04-19 09:17:22
我期望引用應該連續存儲(但我不相信它在任何地方指定)這是類似的事實,即Spec沒有說引用計數不會在任何JVM中用於GC,但是AFAIK沒有。 – 2012-04-19 09:18:35
@ shrini1000如果堆不是連續的虛擬內存塊,則數組跨越兩個片段將不會有連續的佈局。另一方面,堆是連續的並不意味着數組也是這樣,也許只是間接地使它更有可能,因爲GC設計約束是相似的。 – 2012-04-19 09:27:50