java內存中的棧、方法區 、堆


棧(stack):主要保存基本類型(或者叫內置類型)(char、byte、short、int、long、double、float、boolean)和對象的引用,數據可以共享,速度僅次於寄存器(register),快於堆。

方法區(method area):static final 修飾的成員變量都存儲於方法區中,如常量池。

堆(heap):用於存儲對象實例及數組。

方法區:

以String 類型來舉例:          

1 String s1="abc";
2 String s2="abc";
3 String s3=new String("abc");
4 System.out.println("s1和s2 引用地址是否相同:"+(s1 == s2));        //true
5 System.out.println("s1和s2 值是否相同:"+s1.equals(s2));      //true
6 System.out.println("s1和s3 引用地址是否相同:"+(s1 == s3));     //false
7 System.out.println("s1和s3 值是否相同:"+s1.equals(s3));      //true

   內存結構圖如下:                 

                         

  s1 和 s2 地址引用值相等,說明 s1 和 s2 引用的是同一個對象的地址,s3 與 s1 地址引用不等,說明 s3 與其他兩個引用的不是同一個地址。

  java為了避免產生大量的String對象,設計了一個字符串常量池(存在內存中的方法區里)。工作原理是這樣,創建一個字符串時,JVM首先會檢查字符串常量池中是否有值相等的字符串,如果有,則不再創建,直接返回該字符串的引用地址,如果沒有,則創建,然后放到字符串常量池中,並返回新創建的字符串的引用地址,所以上面s1==s2結果為true。

  而 s3 不同的是,JVM首先是在字符串常量池中找 "abc" 字符串,如果沒有則創建字符串常量,如果有則不需要創建;當遇到 new 時,還會在堆內存里面創建一個新的 String 對象,存儲 “abc” ,並將堆內存上String 對象引用的地址返回,所以 s3 與 s1 、s2 引用的不是同一個字符串地址。

   

  本文參考:https://www.cnblogs.com/marsitman/p/11248001.html

  版權聲明:本文版權歸作者所有,歡迎轉載,但請注明出處。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM