内存分析,是说我们的程序在运行时,对内存的使用情况。内存分析是我们编写速度快、效率高的代码必不可少的知识。在我们优化代码的过程中会用到。
jvm(java virtual machine/java虚拟机)内存分四种:
栈区stacksegment:由编译器自动分配释放,存放函数的参数值,局部变量的值等,具体方法执行结束之后,系统自动释放JVM内存资源。
堆区heapsegment:一般由程序员分配释放,存放由new创建的对象和数组,jvm不定时查看这个对象,如果没有引用指向这个对象就回收。
静态区datasegment:存放全局变量,静态变量和字符串常量,不释放。
代码区codesegment:存放程序中方法的二进制代码,而且是多个对象共享一个代码空间区域。
作为对比:
C++内存分为五个区:
堆、栈、自由存储区、全局/静态存储区和常量存储区。
堆:动态存储分配的,由new分配的内存块,它们的释放编译器不去管,而是由应用程序去控制,一般一个new就要对应一个delete。如果程序员没有释放掉,那么在程序结束后,操作系统会自动回收。
自由存储区:就是那些由malloc等分配的内存块,它和堆是十分相似的,不过它是用free来结束自己的生命的。
全局/静态存储区:全局变量和静态变量被分到同一块内存中。
常量存储区:这是一块比较特殊的存储区,它们里面存放的是常量,不允许修改。如果非要修改在C++中也可以利用
const进行修改。
栈:就是那些由编译器在需要的时候分配的,在不需要的时候自动清除的变量的存储区。也就是说那些静态存储分配的局部变量都在这里。
堆:动态存储分配的,由new分配的内存块,它们的释放编译器不去管,而是由应用程序去控制,一般一个new就要对应一个delete。如果程序员没有释放掉,那么在程序结束后,操作系统会自动回收。
自由存储区:就是那些由malloc等分配的内存块,它和堆是十分相似的,不过它是用free来结束自己的生命的。
光看概念,不容易理解,下面结合一个小例子,直观的说一下内存分析。
1. public class Cat { 2. private static int sid = 0;//静态成员变量 3. private String name; 4. int id; 5. Cat(String name) { 6. this.name = name; 7. id = sid++; 8. } 9. public void info(){ 10. System.out.println 11. ("My name is "+name+" No."+id); 12. } 13. public static void main(String arg[]){ 14. 15. Cat.sid = 100;//“类名.”访问的是静态变量。(2.1) 16. Cat mimi = new Cat("mimi"); //(2.2) 17. Cat pipi = new Cat("pipi"); //(2.3) 18. mimi.info(); //(2.4) 19. pipi.info(); //(2.5) 20. } 21. }
1、编译(>javac cat.java)
(1.1)此时会把代码装入内存中的代码区code segment。
(1.2)然后在静态区中,为静态static变量sid分配内存空间。
2、运行(>java Cat)
(2.1)修改静态区中sid的值为100;
(2.2)在堆区heap中开辟一块儿空间放Object,这个空间里有两个变量:name和id;
在栈区static中分配一块儿空间mini:***;
在静态区中存入参数字符串变量"mimi";
修改静态区中的sid为101;
stack中的形参name,在构造方法结束之后就不存在了。
(2.3)类似上图步骤
(2.4)
(2.5)
(2.6)程序释放内存的前一刻,内存中的状态如图所示:
内存分析可能理解的有问题。未完待续。。