轉(zhuǎn)載請(qǐng)出自出處: http://eksliang.iteye.com/blog/2146549
一.java分配內(nèi)存涉及的區(qū)域包括
- 寄存器
- 常量池
- 棧
- 堆
- 靜態(tài)存儲(chǔ)域
二.寄存器介紹
? ? ? 寄存器是最快的內(nèi)存區(qū)域,因?yàn)樗4嬖谔幚砥鲀?nèi)部,這塊區(qū)域我們沒(méi)有直接的控制權(quán),也不可能在代碼里面找到寄存器的任何存在蹤跡,所以這塊不做討論
?
三.常量池介紹
1.常量池是什么?
答:他是在.class文件中開(kāi)避的一塊內(nèi)存區(qū)域,用來(lái)存儲(chǔ)在編譯期間就可以確定一些數(shù)據(jù)
? ? ? ?例如:String str="think";think在編譯的期間就是可識(shí)別的常量,就能加進(jìn)常量池
2.常量池中的數(shù)據(jù)是在什么時(shí)候加載進(jìn)內(nèi)存的?
答:在類被編譯成.class文件時(shí),加載進(jìn)來(lái)的
3.常量池中都放些什么東西?
答:包括如下信息
- String類型的變量;例如String str="think",不是new String("think");
- 對(duì)象的常量值
- 類的全限類名以及他的描述符;屬性的名稱跟描述符;方法的名稱跟描述符
4.String的不變性
1.什么是String的不變性?
答:所謂String的不可變性,是說(shuō)一旦字符串被創(chuàng)建,對(duì)其所做的任何修改都會(huì)生成 新的 字符串對(duì)象(來(lái)源于《think in java》)
接下來(lái)看下他的源碼
public final class String implements java.io.Serializable, Comparable<String>, CharSequence { /** The value is used for character storage. */ private final char value[]; /** Cache the hash code for the string */ private int hash; // Default to 0 /** use serialVersionUID from JDK 1.0.2 for interoperability */ private static final long serialVersionUID = -6849794470754667710L; /** * Class String is special cased within the Serialization Stream Protocol. * * A String instance is written initially into an ObjectOutputStream in the * following format: * <pre> * <code>TC_STRING</code> (utf String) * </pre> * The String is written by method <code>DataOutput.writeUTF</code>. * A new handle is generated to refer to all future references to the * string instance within the stream. */ private static final ObjectStreamField[] serialPersistentFields = new ObjectStreamField[0];
?通過(guò)源碼我們可以看到這個(gè)類他的所有屬性,以及類都是final關(guān)鍵字修飾,也就是說(shuō)他在內(nèi)存中只有一份拷貝,也就是說(shuō)當(dāng)創(chuàng)建一個(gè)新的字符串,他會(huì)去常量池中找如果這個(gè)串存在就直接引用,如果沒(méi)有就創(chuàng)建
例如:如下三句代碼的意思是
1)String s1="aabbcc"; 2) String s2="aabbcc"; 3) s1="aa";
?他的含義入下圖所示:
當(dāng)程序執(zhí)行到(1)時(shí)如圖在常量池中創(chuàng)建"aabbcc"
當(dāng)程序執(zhí)行到(2)時(shí)如圖所示,因?yàn)橐呀?jīng)存在了,就直接引用,(實(shí)際上內(nèi)部在創(chuàng)建一個(gè)字符串時(shí),他會(huì)先去變量常量池,查找看當(dāng)前創(chuàng)建的字符串是否存在,如果存在就直接引用,沒(méi)有就創(chuàng)建)
當(dāng)程序執(zhí)行到(3)時(shí)如圖所示,因?yàn)樾薷牧俗址畇1的值,所以他會(huì)在內(nèi)存中創(chuàng)建一個(gè)新字符串,原來(lái)指向aabbcc的指針斷開(kāi),指向“aa”
?
四.棧
1.棧中存放的是那些數(shù)據(jù)?
答:存放基本類型的變量數(shù)據(jù)和對(duì)象的引用,但對(duì)象本身并不存放在棧中,而是存放在堆中或者常量池中(字符串、常量對(duì)象存放在常量池中)
? ? ? ?當(dāng)在一段代碼塊定義一個(gè)變量時(shí),JVM就在棧中為這個(gè)變量分配內(nèi)存空間,當(dāng)該變量退出該作用域后,JVM會(huì)自動(dòng)釋放掉為該變量所分配的內(nèi)存空間,該內(nèi)存空間可以立即被另作他用。
2.實(shí)際存儲(chǔ)在哪里?
答:數(shù)據(jù)駐留在RAM(隨機(jī)存儲(chǔ)器)區(qū)域;
何為隨機(jī)存儲(chǔ)器?答:是與CPU直接交換數(shù)據(jù)的內(nèi)部存儲(chǔ)器,也叫主存或者內(nèi)存,它可以隨時(shí)讀寫(xiě),而且速度很快,通常作為操作系統(tǒng)或正在運(yùn)行中的程序的臨時(shí)數(shù)據(jù)存儲(chǔ)媒介
?
五.堆
1.存放的是那些數(shù)據(jù)?
答:存放所有new 出來(lái)的對(duì)象。或者通過(guò)反射創(chuàng)建的對(duì)象
2.實(shí)際數(shù)據(jù)存儲(chǔ)在哪里?
答:數(shù)據(jù)駐留在RAM(隨機(jī)存儲(chǔ)器)區(qū)域
?
六.靜態(tài)存儲(chǔ)域
1.存放的是那些數(shù)據(jù)?
答:存放的是靜態(tài)成員(static定義),這兒的靜態(tài)(static)是指"位置固定位置"。程序運(yùn)行期間,靜態(tài)存儲(chǔ)的數(shù)據(jù)將隨時(shí)等候調(diào)用。可用static關(guān)鍵字指出一個(gè)對(duì)象的一個(gè)屬性或者方法是靜態(tài)的,但是JAVA對(duì)象永遠(yuǎn)不會(huì)保持到靜態(tài)存儲(chǔ)區(qū)
?
?
?
?
??
更多文章、技術(shù)交流、商務(wù)合作、聯(lián)系博主
微信掃碼或搜索:z360901061

微信掃一掃加我為好友
QQ號(hào)聯(lián)系: 360901061
您的支持是博主寫(xiě)作最大的動(dòng)力,如果您喜歡我的文章,感覺(jué)我的文章對(duì)您有幫助,請(qǐng)用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點(diǎn)擊下面給點(diǎn)支持吧,站長(zhǎng)非常感激您!手機(jī)微信長(zhǎng)按不能支付解決辦法:請(qǐng)將微信支付二維碼保存到相冊(cè),切換到微信,然后點(diǎn)擊微信右上角掃一掃功能,選擇支付二維碼完成支付。
【本文對(duì)您有幫助就好】元
