这里我们主要关心栈,堆和常量池。
基础类型的变量和常量以及变量和引用存储在栈中;常量存储在常量池中;对象存储在堆中。
栈中的数据大小和生命周期是可以确定的,当没有引用指向数据时,这个数据就会消失。堆中的对象的由垃圾回收器负责回收,因此大小和生命周期不需要确定,具有很大的灵活性。
对象的引用存在栈中;编译期直接用双引号定义的存在常量池中;运行期new出来的存在堆中。
内容相同的字符串在常量池中只有一份,而在堆中可以存在多份。看下面例子:
String s1 = "china"; String s2 = "china"; String s3 = "china"; String ss1 = new String("china"); String ss2 = new String("china"); String ss3 = new String("china");
int i1 = 9; int i2 = 9; int i3 = 9; public static final int INT1 = 9; public static final int INT2 = 9; public static final int INT3 = 9;
成员变量存储在堆中的对象里面,由垃圾回收器负责回收。
class BirthDate { private int day; private int month; private int year; public BirthDate(int d, int m, int y) { day = d; month = m; year = y; } // 省略get,set方法……… } public class Test { public static void main(String args[]) { int date = 9; Test test = new Test(); test.change(date); BirthDate d1 = new BirthDate(7, 7, 1970); } public void change1(int i) { i = 1234; } }
对于以上这段代码,date为局部变量,i,d,m,y都是形参为局部变量,day,month,year为成员变量。下面分析一下代码执行时候的变化: