Difference in static initialization order depending on main class in Java inheritance hierarchy [duplicate]

1 day ago 1
ARTICLE AD BOX

Look, the code you've posted is an incredibly complex maze that only serves to say, "Look, I managed to create this maze without any problems of interdependence" but it won't help you understand the "chronological order" of events. Let's try a simpler example, which will evolve over time:

But first, a quick clarification: you say, "In code 1, where the main method is inside class A1, the JVM initially only ‘sees’ A1", and no, before doing anything, the JVM loads all the structures of all classes into memory, and only after doing so does it proceed to instantiate the attributes as needed, and of course, the first ones it instantiates are those of the class that is "marked" as the main class.

First, the "immutable" class:

class Greeting { public Greeting( String word ) { System.out.println( word ); } }

Now the "mutable" class:

public class Main { Greeting byebye = new Greeting( "Bye bye" ); static Greeting welcome = new Greeting( "Welcome" ); public Main() { System.out.println( "Main constructor" ); } public static void main( String[] args ) { } }

If you run this code, you'll see that it prints:

Welcome

This shows us that the first thing the JVM does is instantiate the static variables, and it does nothing else until an object is created.

So let's modify our class to create an object and see what happens (only the main method):

public static void main( String[] args ) { new Main(); }

Now print:

Welcome Bye bye Main constructor

From this, we can conclude that after initializing all the static variables, it initializes all the attributes, and only after finishing with those does it execute the constructor code.

It's important to know this so you can understand that by the time execution reaches the constructor, the object has already been created with all its variables and attributes instantiated, some with values assigned in the class body and others with default values.

Now, if I may speculate, I think what\s been confusing you is actually quite basic, it has to do with the order in which code is executed, or more precisely, the order in which statements are executed when one method calls another.

Let's look at another one of my simple examples:

void methodA() { System.out.println( "Method A first line" ); methodB(); System.out.println( "Method A second line" ); } void methodB() { System.out.println( "Method B first line" ); methodC(); System.out.println( "Method B second line" ); } void methodC() { System.out.println( "Method C first line" ); System.out.println( "Method C second line" ); }

This print:

Method A first line Method B first line Method C first line Method C second line Method B second line Method A second line

Here we see how execution jumps between methods: it executes the first line of methodA, "jumps" to methodB, executes its first line, and then "jumps" to methodC, which executes its two lines, and returns control to methodB, which executes its second line and returns control to methodA, which executes its second line... and returns control to the caller (this is fundamental to understanding recursion).

The only exception to this way of "chaining" executions is the creation of threads; these have a "life" of their own and do not return control to the one who created them.

Read Entire Article