My teacher gave me a question:
"What occurs when objects are created in Java".
To the best of my knowledge, memory allocation, variable initialization and constructor method invocation happen when an object is created.
But my teacher said that I was almost right. The 2 later things are right, except memory heap. Instead, he said the memory allocation occurs. I think that object is stored in heap, so my teacher is wrong. Do you think so?
As always, the best place to find a solution for these kinds of questions is in the Java Language Specification.
Specifically, from the section on new instance creation, it can be understood that this is the sequence when a new object is created, as long as no exceptions occur:
Memory is allocated.
Fields are initialized to their default values.
The "first line" of the chosen constructor is invoked, unless it's an Object. By first line I mean either explicit call to super() or this(), or an implicit call to super().
The instance initializer is executed and the fields are initialized to their requested values (actually field initialization is usually compiled as an inline part of the instance initializer).
The rest of the constructor code is executed.
Now, it is possible that your teacher is talking about memory allocation as an actual operating system call - and in that case he's right in the sense that the JVM manages its own heap and thus a Java memory allocation does not necessarily translate to an OS memory allocation call (although it may).
I'll answer that using a simple example.
Say you have a class Car. Now you write:
Car car;
car = new Car();
The first statement creates a reference with car in the stack.
In the second statement, the Car class will be loaded to the main memory, then it will allocate memory for the members of Car in the heap. When this happens, the members will be initialized with values provided by the JVM.
While the JVM is running the program, whenever a new object is created, the JVM reserves as portion of the Heap for that object (where the object will be stored). The amount of Heap that gets reserved is based on the size of the object.
The JVM maps out this segment in the Heap to represent all of the attributes of the object being stored. A reference (address in Heap) to the object is kept by the JVM and stored in a table that allows the JVM to keep track of all the objects that have been allocated on the Heap. The JVM uses these references to access the objects later (when the program accesses the object).
On top of what other people have said, if this is the first use of the object then its Class must be initialised -as described in the JLS (the section before the one on new instance creation!).
This basically involves loading into memory the necessary information about the class i.e. creating a Klass object for the static variables and method table to live. This may also involve loading super classes and interfaces. This is all carried out by the ClassLoader.
When object is created in java then these 6 step will be happens one by one---
1.JVM allocates 8 bytes of memory for the reference variable & assign default value as null.
JVM will verify whether class loading is done or not,if class is already loaded then it will ignore or else it will perform class loading.
At the time of class loading ,if any static variable are there then it will allocating memory.
By using new operator,object memory will e created inside heap memory.
At the time of object creation,if any instance variables are there then those will allocate memory inside object Memory.
It will assign object memory address to the reference variable which is created first.
Related
I am a bit confused GC aspect when it comes to the instance variables, especially fields.
So, if an object holds references to its field objects, these won't be eligible for garbage collection until the object itself is. Since Threads are GC roots and every object must have been created on some Thread only, thread won't let go of any objects created on it and the entire object hierarchy from a Thread shall remain for a considerable time before getting garbage collected.
On the other hand, if an object lets go of the field objects, calling a getter for these objects will end up in returning null later.
So, what are the facts here?
Clarification for "field objects"(as asked in comments)
By field objects I mean, the field members of an object that are themselves objects
Edit 2: A bit more elaboration
So, you see Threads are execution units having representation in memory through the Thread object instance. Any code execution that is happening anywhere is happening on some Thread.
How would this execution happen?
Well, through the execution of some code in a method. What would that make this object created?
A Local variable
And, that would make it a GC root.
Btw, for a method call, there is a stack for that particular call and this is what I have been referring to here.
It ain't so simple as #louis-wasserman said - "Yes, naturally" or for that matter not that natural..(?)
I investigated some more and found the answer on...where you would expect it probably - Java Language Specification
2.7. Representation of Objects
The Java Virtual Machine does not mandate any particular internal
structure for objects.
In some of Oracle’s implementations of the Java Virtual Machine, a
reference to a class instance is a pointer to a handle that is itself
a pair of pointers: one to a table containing the methods of the
object and a pointer to the Class object that represents the type of
the object, and the other to the memory allocated from the heap for
the object data.
Yes, that settles it. Even though, JLS doesn't mandate on the internal structure of an java.lang.Object, it would be likely that a structure similar to Oracle's JVM might be used.
This has bigger implication that you might think. Imagine a very heavy object holding one very bulky member field object. Hmmm...a Bitmap maybe. A Bitmap of 10MB and the other object simply holds the image's title:
bulky_object = {bitmap, title}
If you create up this object as a local variable inside a method inside a nested scope(for example's sake), the container object is eligible for garbage collection after the scope gets over but if you decide to hold a reference to the bitmap(the field) object after the scope, the containing object won't have been collected fully:
void someMethod(){
// Outer block of the method
bitmap_ref;
// Nested block starts
{
some_object = new some_object();
// Hold a ref to the bitmap
bitmap_ref = some_object.bitmap;
}
// Nested block has ended. some_object is eligible for GC and is not accessible as a GC root
// anymore
// bitmap_ref shall remain available alive and well here as we are holding a ref to it
// Also, some_object garbage collection may have happened leaving bitmap_ref alive
}
This would seem like an object leak here.
I know JVM uses stack and heap for allocation of memory for object reference, object value and memory for methods. But I am confused about the terminologies: METHOD AREA, HEAP and JAVA STACK and I have few question's.
When we say "ClassName obj = new ClassName()", new creates an object on the HEAP(the instance variables and static variables too) and what is returned to the reference(obj)? Some people use to say it is CLASS TYPE, does it mean the hash code?
When new creates the object on the heap, at the same time: i)the methods,corresponding to that object ii)local variables and iii)the reference to that object are stored as part of STACK( is it JAVA STACK?). If so, then what does METHOD AREA do? Or am I wrong?
What is the amount of memory allocated for that object?
i. for object reference
ii. for object values(it depends on the local variables)
iii. will there be a memory allocated to point the object's methods?( because the non-static members are not shared among the objects and a separate copy is maintained for each objects including the methods).
By the way, where does static methods are stored?
When we say "ClassName obj = new ClassName()", new creates an object
on the HEAP(the instance variables and static variables too) and what
is returned to the reference(obj)? Some people use to say it is CLASS
TYPE, does it mean the hash code?
Yes new creates Object on the HEAP. Heap is a memory place where the objects and its instance variable are stored. Not static variables since static variables doesn't belong to Object it belongs to class so are stored on PermGem Sections (class related data, not instance related).
What is Returned : the reference(pointer/memory address) i.e hashcode
When new creates the object on the heap, at the same time: i)the
methods,corresponding to that object ii)local variables and iii)the
reference to that object are stored as part of STACK( is it JAVA
STACK?). If so, then what does METHOD AREA do? Or am I wrong?
since All threads share the same method area methods don't corresponds to Objects it belongs to class
what does METHOD AREA do :The method area stores per-class information, like Run Time Constant Pool, Method code, The method's return type (or void) etc
What is the amount of memory allocated for that object? i. for object
reference ii. for object values(it depends on the local variables)
iii. will there be a memory allocated to point the object's methods?(
because the non-static members are not shared among the objects and a
separate copy is maintained for each objects including the methods).
Amount of Memory for Object Reference: it depends as on many VMs the size of a reference is the native pointer size and for (iii) above point already cleared that
I know JVM uses stack and heap for allocation of memory for object reference
correct.
object value
I assume you means the object's header and fields.
and memory for methods.
Methods are not stored in the heap, or stack. When you profiler the heap usage or set the maximum heap size, the use of methods makes no difference as they are not on the heap in the Oracle or OpenJDK JVM.
They are stored in the PermGen or MetaSpace or some other space depending on which JVM you are using.
But I am confused about the terminologies: METHOD AREA,
From Method Area in Java
The Java Virtual Machine has a method area that is shared among all Java Virtual Machine threads. The method area is analogous to the storage area for compiled code of a conventional language or analogous to the "text" segment in an operating system process. It stores per-class structures such as the run-time constant pool, field and method data, and the code for methods and constructors, including the special methods (§2.9) used in class and instance initialization and interface initialization.
HEAP
Shared space for storing objects. This is usually one continuous region of native memory managed by the JVM.
and JAVA STACK
The thread's stack which is actually a native thread stack on most JVM.
When we say "ClassName obj = new ClassName()", new creates an object on the HEAP(the instance variables and static variables too)
It might, but it can also eliminate the object with escape analysis, placing the fields on the stack, and possibly eliminating those.
and what is returned to the reference(obj)?
Correct, Java only has references and primitives (if you ignore the void type which is neither)
Some people use to say it is CLASS TYPE,
The reference is defined by giving the type of the reference which is a class or interface.
does it mean the hash code?
A hash code is a hash value for the object. It is not releated to anything else you have mentioned.
When new creates the object on the heap,
When you create a new object on the heap, you just create space for the header of the object (which points to the class and it's methods) and space for it's fields. (Those the JVM doesn't optimise away)
at the same time: i)the methods
The methods are loaded/compiled in various stages. The methods are loaded as they are needed for the first time and later if they are compiled.
corresponding to that object ii)local variables
Local variables are on the stack, not on the heap, not in the object.
iii)the reference to that object are stored as part of STACK( is it JAVA STACK?).
The Java Stack, is the Stack, is the native stack.
If so, then what does METHOD AREA do?
Store the code for the methods.
What is the amount of memory allocated for that object?
About 8-12 bytes per header, space for each primitive field and reference and alignment padding of 8 or 16 bytes (32 GB - 64 GB heaps).
i. for object reference
Typically this is 32-bit on 64-bit JVMs (With compressed oops). If you have more than 64 GB heap it will be 64 -bit.
ii. for object values(it depends on the local variables)
Local variables are on the heap not the object.
iii. will there be a memory allocated to point the object's methods?
Method memory usage is not visible to you. It is not on the heap, nor something you can measure on a per method basis. I don't know of a profiler which will even show you this.
( because the non-static members are not shared among the objects and a separate copy is maintained for each objects including the methods).
That sounds like an insane waste of space, and it is, which is why the JVM does do that. There is only one copy for a method, regardless of the number of instances.
By the way, where does static methods are stored?
With all the other methods. There is no difference between a static method and a non-static method except a non-static method must take an instance as it's first argument at the JVM level. (And there is a bit in the modifiers to say whether it is static or not)
Let's say I have this code:
{
int var = 2;
// more code
}
What happens with 'var' after the code is executed and it is not used anymore? Is it deleted from memory or it stays there occupying memory, or something else?
Related to this, is it better to work with variables that way^, or to make some global variable and just change it's value?
Local variables live on the stack. If it's a reference to an object then only variable is on the stack.
Instance variables live on the heap because they belong to an object.
Also this post (Stack and heap memory in java) might be helpful.
To make a long story short, in java (and other JVM languages), you don't have to care about memory allocation and dealocation at all. You really shouldn't be worrying about it. Once you lose the reference to that variable (in this case, when the method call ends), the variable is effectively gone. Some indefinite amount of time after that, the Garbage collecting thread will notice that you can't possibly access that variable anymore, and free up the memory it was using.
See: Garbage Collection in Java.
if you are defining any variable as instance variable then that variable will be used by instance. and instance will be saved in Heap memory area.
Garbage collector will run periodically to clean non referenced object from memory.
but if that variable is defined inside any block or method then that will be stored Stack memory.
Java Stack memory is used for execution of a thread. They contain method specific values that are short-lived and references to other objects in the heap that are getting referred from the method. Stack memory is always referenced in LIFO (Last-In-First-Out) order. Whenever a method is invoked, a new block is created in the stack memory for the method to hold local primitive values and reference to other objects in the method. As soon as method ends, the block becomes unused and become available for next method.
Everything in Java is removed from memory when it is no longer referenced. It takes a lot of effort to cause true memory leaks in Java.
Java primitives like int, boolean, and char are put on the stack and removed from memory as soon as they leave scope. Java objects like String, arrays, or ArrayList are allocated on the heap (and referenced by the local variable on the stack). Objects are garbage collected (removed from memory) when there is no longer a reference to them.Static variables belong to a class and will be a reference an object as long as the class is loaded, which is usually the entire run time of the Java program. Statics are the closest thing Java has to global variables, but overuse or misuse of statics is actually a way to cause memory issues rather than solve them.
Whenever a class is loaded, what are stored in the heap and what are stored in the stack ?
Also where does the threads reside ?
Reference types are in heap.
Any primitive type data and references to values on heap (parameters / local variables of method) are on the stack.
Each thread has its own stack.
All threads in the application share same heap.
It's really easy:
objects (i.e. instances of classes) are always on the heap. They can't be anywhere else
fields are part of objects, so they also live on the heap.
local variables (including method/constructor) parameters are always on the stack. They can't be anywhere else.
Note that local variables can only hold references ("pointers") or primitive values. A local variable can't ever hold "an object".
Note that this view is what is defined in the JVM specification. A concrete JVM could allocate objects in a non-heap area if it wants to. For example: if it knows that a newly created object never escapes the current invocation, then it could put the instantiated object in the stack area. However, that's a very optimization that is not visible to the developer.
Primitives :Stack
Objects : Heap
Threads : Have a separate stack while share the same heap.
If my application has too many static variables or methods, then as per definition they will be stored in heap. Please correct me if I am wrong
1) Will these variables be on heap until application is closed?
2) Will they be available for GC at any time? If not can I say it is a memory leak?
Static methods are just methods, they are not stored on the heap, they just don't get to use a "this" parameter.
Static variables serve as "roots" to the GC. As a result, unless you explicitly set them to null, they will live as long as the program lives, and so is everything reachable from them.
A situation is only considered a memory leak if you intend for the memory to become free and it doesn't become free. If you intend for your static variable to contain a reference to an object for part of the time, and you forget to set it to null when you're done with that object, you would likely end up with a leak. However, if you put it in the static variable and intend for it to be there for as long as the program is running, then it is most definitely not a leak, it is more likely a "permanent singleton". If the object got reclaimed while you wanted it to still exist, that would have been very bad.
As for your question about the heap: All objects in Java exist either on the heap or on the stack. Objects are created on the heap with the new operator. A reference is then attached to them. If the reference becomes null or falls out of scope (e.g., end of block), the GC realizes that there is no way to reach that object ever again and reclaims it. If your reference is in a static variable, it never falls out of scope but you can still set it to null or to another object.
If you have a static hashmap and you add data to it... the data will never disappear and you have a leak - in case you do not need the data anymore. If you need the data, it is not a leak, but a huge pile of memory hanging around.
Objects directly or indirectly referenced by statics will remain on the heap until the appropriate class loader can be collected. There are cases (ThreadLocal, for instance) where other objects indirectly reference the class loader causing it to remain uncollected.
If you have a static List, say, and add references to it dynamically, then you can very easily end up with "object lifetime contention issues". Avoid mutable statics for many reasons.
As long as you can reference these variables from somewhere in the code it can't by GCed which means that they will be there until the end of the application.
Can you call it a memory leak, I wouldn't call it a memory leak, usually a memory leak is memory that you normally expect to recover but you never do, or you only recover part of it. Also memory leaks usually get worse in time (eg: every time you call a method more memory is "leaked") however in this case the memory usage for those variables is (kind of) static.
It won't cause a memory leak in the classic C sense... For example
Class A{
static B foo;
...
static void makeFoo(){
foo = new B();
foo = new B();
}
In this case, a call to makeFoo() won't result in a memory leak, as the first instance can be garbage collected.