JVM内存结构及java相关基础知识
2012-03-10 21:16
555 查看
1. JVM , JRE和JDK
JVM:加载class文件并进行解析
JRE(java running environment):JVM+API (java核心类库)
JDK:JRE+工具(包括javacjavadoc等工具)
2. java内存区
包括方法区、java堆、java栈、PC寄存器、本地方法栈。
方法区(或者叫永久代permanent generation):包括类信息、方法信息(如一些private修饰之类的)、常量池、静态变量和class loader的引用。常量池指的是在编译期被确定,并被保存在.class文件中的一些数据。所以如果可以从常量池中取就不要去new一个。如Integeri=Integer.valueOf(10)会比Integer i=new Integer(10)好。这部分数据是所有线程共享的。
java堆:存放对象实例,所有的实例和数组都是在堆上分配的。Java堆和方法区一样是被所有线程共享的。Java堆有更细致的划分:新生代(采用minor gc)、老龄代(采用full gc),无论对java堆如何划分都是为了更好的回收内存,或更快的分配内存。根据VM Spec的要求,java 堆可以处于内存上不连续的空间,只要逻辑上连续即可。如果在堆中无法分配内存将会报OutOfMemeryError。
Java栈:存了很多栈帧。一个栈帧对应了java中的方法。栈帧包括局部变量、操作数栈(对数据的计算操作)、栈数据区(存放异常信息和解析静态变量--与方法区沟通)。每个方法被执行的时候都会创建一个栈帧,一个方法的调用至完成对应了栈帧的入栈至出栈过程。默认的栈大小是128K,可以手动配置。如果线程请求(比如线程栈1中的age是10,线程栈2的age是20)的栈深度大于栈大小,将抛出StackOverflowError。
PC寄存器:每个java线程都有一个PC寄存器用于保存程序执行到哪一个指令,对于非native的方法,这个区域记录的是正在执行的地址。
本地方法栈:为本地使用的方法服务,与java栈作用相同。会先去找本地方法接口,再通过本地方法接口调用本地方法,这里就体现了JVM的跨平台,本地方法接口可以有不同的实现。
3. 结合JVM内存,解释为什么在java中,说String是不可变的。
比如String s =new String(“wo”);String s1 = new String(“de”);
s = s + s1;
JVM:加载class文件并进行解析
JRE(java running environment):JVM+API (java核心类库)
JDK:JRE+工具(包括javacjavadoc等工具)
2. java内存区
包括方法区、java堆、java栈、PC寄存器、本地方法栈。
方法区(或者叫永久代permanent generation):包括类信息、方法信息(如一些private修饰之类的)、常量池、静态变量和class loader的引用。常量池指的是在编译期被确定,并被保存在.class文件中的一些数据。所以如果可以从常量池中取就不要去new一个。如Integeri=Integer.valueOf(10)会比Integer i=new Integer(10)好。这部分数据是所有线程共享的。
java堆:存放对象实例,所有的实例和数组都是在堆上分配的。Java堆和方法区一样是被所有线程共享的。Java堆有更细致的划分:新生代(采用minor gc)、老龄代(采用full gc),无论对java堆如何划分都是为了更好的回收内存,或更快的分配内存。根据VM Spec的要求,java 堆可以处于内存上不连续的空间,只要逻辑上连续即可。如果在堆中无法分配内存将会报OutOfMemeryError。
Java栈:存了很多栈帧。一个栈帧对应了java中的方法。栈帧包括局部变量、操作数栈(对数据的计算操作)、栈数据区(存放异常信息和解析静态变量--与方法区沟通)。每个方法被执行的时候都会创建一个栈帧,一个方法的调用至完成对应了栈帧的入栈至出栈过程。默认的栈大小是128K,可以手动配置。如果线程请求(比如线程栈1中的age是10,线程栈2的age是20)的栈深度大于栈大小,将抛出StackOverflowError。
PC寄存器:每个java线程都有一个PC寄存器用于保存程序执行到哪一个指令,对于非native的方法,这个区域记录的是正在执行的地址。
本地方法栈:为本地使用的方法服务,与java栈作用相同。会先去找本地方法接口,再通过本地方法接口调用本地方法,这里就体现了JVM的跨平台,本地方法接口可以有不同的实现。
3. 结合JVM内存,解释为什么在java中,说String是不可变的。
比如String s =new String(“wo”);String s1 = new String(“de”);
s = s + s1;
首先系统在堆上new出一个数组来存放“wo”,在栈中有个变量s指向堆中的“wo”对象,栈中的s1指向“de”对象;当执行s=s+s1时,系统重新在堆中new出一个更大的数组对象,然后将“wo”和“de”都复制进去,然后栈中的s指向这个新的对象。所谓的不可变是指:它没有在原数组“wo”上进行修改,而是新建了个更大数组进行扩展,也就是说,这时候堆里还是有“wo”这个对象数组存在的,只不过这个时候"s"变量不在指向"wo"这个数组了,而是指向了新new出来的数组,这就是和StringBuffer的区别,后者是在原数组上进行修改,改变了原数组的值,StringBuffer不是通过新new一个数组去复制,而是在原数组基础上进行扩展...再让变量指向原数组。
相关文章推荐
- Java基础知识强化100:JVM(Java虚拟机)内存体系 与 对象访问
- java的线程安全、单例模式、JVM内存结构等知识学习和整理
- java线程基础巩固---多线程与JVM内存结构的关系及Thread构造函数StackSize的理解
- java的线程安全、单例模式、JVM内存结构等知识学习和整理
- Java JVM:内存结构和相关参数
- Java基础——JVM内存结构
- JVM基础知识1--JAVA内存区域与内存溢出异常
- java基础—JVM内存结构,为什么需要GC?
- Java JVM:内存结构和相关参数含义
- [置顶] java的线程安全、单例模式、JVM内存结构等知识学习和整理
- java基础知识(三)jvm 内存空间+对象+GC
- Java相关的基础知识
- Java基础---java虚拟机内存结构
- JAVA相关基础知识
- java基础知识记录--类相关语法 (摘自张孝祥整理java面试题)
- Java学习之ACM相关基础知识
- JAVA相关基础知识
- Java基础知识-3、运算符与选择结构
- Java工程师应该掌握的相关知识(基础篇01)
- 【Java核心计算 基础知识(第9版)】第3章 Java的基本程序设计结构