I am confused regarding whether memory allocation in java occurs at run time or compile time.
For example:
class Test{
int a;
public Test(){
Well, this one is a bit of a doozy and I'm not sure that you're going to get the exact answer that you want out of this entire thread, since really, what you're asking, is a major discourse in the internals of the compiler, and most people really don't care.
For the most part, the Java Compiler uses automatic memory management, so it's really up to the compiler to determine what it will or will not do, and this can change between versions.
But before I start explaining this, I want to clarity my notation:
String is a special case in java, and although it is an object, it may be treated differently than other objects.
An [object] has a special property. It has a value and an identifier, and the process by which an identifier is resolved to a value and at which time it occurs depends on the type of binding.
There is static binding, in which the binding can be resolved at compile time and the value or method of which is known at compile time. This is also known as "early" binding. For example.
int a = 0; // AND //a direct function call, like print();
There is also dynamic binding, in which the binding between an identifier and a value or a subprogram to a program cannot occur until runtime. This is also known as "late" binding. For example.
public void foo(java.util.List list) { list.add("bar"); }
There's also a hybrid kind of binding, but I'm not going to talk about that because I haven't discovered Java to have it.
Now, binding is also very closely related to scoping, which is the idea that a variable "lives" in a certain scope. That's a topic of discourse I really don't want to go into (scoping is kind of a bear) and make this post a novel rather than a novella.
The way memory allocation in Java works depends on a few things:
If the reference to an [Object], [object], or [primitive] is known at compile time, and is it possible for static binding to occur, then the compiler is likely to allocate memory for those objects (notice how I didn't use brackets) at compile time.
If the reference to an [Object], [object], or [primitive] cannot be known at compile time, and dynamic binding must be used, then the compiler is likely to allocate memory for those objects at runtime.
The way that Java treats objects allocated at runtime differentiates depends on which binding was used for what type.
In summary, don't worry about it. It's a big headache for you to do so.
If I'm wrong about any of this, someone please let me know. I'm a little bit rusty.