定义一个hashtable的静态变量,value放置的是对象。
关于内存分配我的理解是:
该变量的定义是放在栈里的,包括对各对象的引用地址,然后真正的对象是放在堆中的,不知道对不对?
主要我的设计必要需要静态变量共享,然后该table封装的对象也是很多且都较大的,所以我就必须搞懂这个问题。
多谢大家帮助。
关于内存分配我的理解是:
该变量的定义是放在栈里的,包括对各对象的引用地址,然后真正的对象是放在堆中的,不知道对不对?
主要我的设计必要需要静态变量共享,然后该table封装的对象也是很多且都较大的,所以我就必须搞懂这个问题。
多谢大家帮助。
class Test
{
public static List list = new ArrayList();
}变量list在非堆中(方法区),指向的实际对象在堆中。跟栈没有任何关系。
Stack(栈)、Heap(堆) 吗?还有一个方法区啊?多谢你作答。
变量之类的都放在Heap里
class Test{
int i;//自然要随对象分配在堆里
publi void test(){
int j;//方法执行时才分配空间,在栈里
}
}
class Test{
int i;//Test类对象在堆中,所以成员变量(全局变量)i在堆中,这个容易理解
public static List list = new ArrayList();//此处的成员变量在方法区,是因为static的原因么?
publi void test(){
int j;//方法中的局部变量j在方法执行时才分配空间,所以在栈里
}
}那么是否可以这样理解:
1.如果类的成员变量不是静态的,那么该成员变量在对象生成时,随对象在堆中开辟一块空间存储
2.如果类的成员变量是静态的,那么在类加载时,在方法区中会开辟一块空间存储该静态变量
恳请ZangXT大侠指教?
class Test{
int i;//Test类对象在堆中,所以成员变量(全局变量)i在堆中,这个容易理解
public static List list = new ArrayList();//此处的成员变量在方法区,是因为static的原因么?
publi void test(){
int j;//方法中的局部变量j在方法执行时才分配空间,所以在栈里
}
}那么是否可以这样理解:
1.如果类的成员变量不是静态的,那么该成员变量(基本类型),或者该变量的引用,在对象生成时,随对象在堆中开辟一块空间存储
2.如果类的成员变量是静态的,那么在类加载时,在方法区中会开辟一块空间存储该静态变量(基本类型)或者该变量的引用,该引用所指向的对象在堆中
恳请ZangXT大侠指教?
int a = 0;
这样一句就是直接存储了该变量的值到内存栈的
A a = new A();
只有这样的格式才会存在将引用存到内存栈,将对象内从存储到内存堆里面。至于Java里面的静态变量、实例变量、块变量和局部变量不是根据它的存储方式来划分的,主要在于它的生命周期,根据不同的生命周期进行变量的划分,静态变量是属于类的,所以只要类加载器一旦加载了它就有效了,具体内容你可以参考我BLOG上边Java的类和对象里面关于对象生命周期的章节,可能会有一个更加深入的了解:
http://blog.csdn.net/silentbalanceyh/archive/2009/09/24/4587371.aspx
堆内存用来存放由new创建的对象和数组,在堆中分配的内存,由java虚拟机的自动垃圾回收器来管理。在堆中产生了一个数组或者对象之后,还可以在栈中定义一个特殊的变量,让栈中的这个变量的取值等于数组或对象在堆内存中的首地址,栈中的这个变量就成了数组或对象的引用变量,以后就可以在程序中使用栈中的引用变量来访问堆中的数组或者对象,引用变量就相当于是为数组或者对象起的一个名称。引用变量是普通的变量,定义时在栈中分配,引用变量在程序运行到其作用域之外后被释放。而数组和对象本身在堆中分配,即使程序运行到使用new产生数组或者对象的语句所在的代码块之外,数组和对象本身占据的内存不会被释放,数组和对象在没有引用变量指向它的时候,才变为垃圾,不能在被使用,但仍然占据内存空间不放,在随后的一个不确定的时间被垃圾回收器收走(释放掉)。这也是java比较占内存的原因。
Java就在栈中为这个变量分配内存空间,当超过变量的作用域后,java会自动释放掉为该变量分配的内存空间,该内存空间可以立即被另作它用
但是看你很多基本概念都没弄明白,比如你根本分不清什么是引用,什么是对象,甚至认为this和super是两个“内置对象”。
好好看书吧
所谓分不清引用和对象是我看错了,没看明白“有这样的格式才会存在将引用存到内存栈,将对象内从存储到内存堆里面。”这句话的后半部分。
不礼貌,道歉。
static Object o = new Object(); //线程执行到这里的时候,o的变量在哪里,new Object()在哪里? 各在内存在栈、堆、方法区?
多谢。
运行时数据区域,所有类实例和数组的内存均从此处分配。Java 虚拟机启动时创建。对象的堆内存由称为垃圾回收器 的自动内存管理系统回收。
组成
News Generation (Young Generation即图中的Eden + From Space + To Space)
Eden 存放新生的对象
Survivor Space 两个 存放每次垃圾回收后存活的对象
Old Generation (Tenured Generation 即图中的Old Space) 主要存放应用程序中生命周期长的存活对象非堆内存
JVM具有一个由所有线程共享的方法区。方法区属于非堆内存。它存储每个类结构,如运行时常数池、字段和方法数据,以及方法和构造方法的代码。它是在 Java 虚拟机启动时创建的。
除了方法区外,Java 虚拟机实现可能需要用于内部处理或优化的内存,这种内存也是非堆内存。 例如,JIT 编译器需要内存来存储从 Java 虚拟机代码转换而来的本机代码,从而获得高性能。
组成
Permanent Generation (图中的Permanent Space) 存放JVM自己的反射对象,比如类对象和方法对象
native heap 希望有所帮助
每个线程有一个自己的栈。Object o = new Object(); //线程执行到这里的时候,o的变量在哪里,new Object()在哪里?
如果该声明是在方法中的话,o是个局部引用变量(或者说就是指针,地址),存在于线程的栈里。实际对象在堆中。如果该声明是在类定义中的话,
比如
class Test{
Object o = new Object();
}
o是个nonstatic field,引用o作为Test对象的一部分存在于堆中,而o指向的new Object 也在堆中,但不是上面提到的o所在Test对象的一部分。static Object o = new Object();
o在方法区,实际对象在堆中。
让我理解了一些。
类的对象产生时,堆内存中开辟一块空间存放该对象,以及该对象的成员变量,如果该成员变量是个引用,那么这个引用所指向的实际对象也在堆内存中2.类的静态成员变量
JVM加载该类时,方法区开辟一块空间存放该变量,如果该成员变量是个引用,那么这个引用所指向的实际对象在堆内存中3.方法中的局部变量
线程执行到该变量声明语句时,栈内存中开辟一块空间存放该变量,如果该局部变量是个引用,那么这个引用所指向的实际对象在堆内存中
http://blog.csdn.net/silentbalanceyh/archive/2009/10/13/4661230.aspx
主要分为Java内存模型的,你可以仔细看看