This is the sixth day of my participation in the August Text Challenge.More challenges in August

I did the sequence of code blocks and constructors in the interview before. Although I was half-guessing right at that time, I did not have a special understanding of this, so I wanted to see if I could thoroughly understand it today, which would help everyone and myself.

A simple question

In Java, there are static code blocks, non-static code blocks (construction code blocks), normal code blocks, and static variables and member variables. Do you really understand the order in which these code blocks and variable assignments are executed?

In the code

public class Address {
    private String province;
​
    public Address(String province) {
        this.province=province;
        System.out.println("-- Address 的构造方法:province="+this.province+"");
    }
​
}
Copy the code
public class User { private static final Address address1=new Address("guangdong"); private Address address2=new Address("guangxi"); Static {system.out.println ("-- User static code block 1--"); } {system.out.println ("-- User non-static code block 1--"); } public User() {{system.out.println ("-- User code block 1--"); } system.out.println ("-- User constructor --"); {system.out.println ("-- User plain block 2--"); } } private static final Address address3=new Address("hubei"); private Address address4=new Address("hunan"); {system.out.println ("-- User non-static code block 2--"); } static {system.out.println ("-- User static code block 2--"); }}Copy the code
Public class StaticCodeTest {/** * static code block, non-static code block, constructor, static variable, member variable execution order. */ public static void main(String[] args) { new User(); }}Copy the code

You can write down your answers first.

Come and check the answer!

-- type =guangdong -- User -- -- type =hubei -- User -- -- Address -- -- Address :province=hunan -- User nonstatic code block 2-- -- User common code block 1-- -- User Constructor -- -- User plain block 2-- plain block 2--Copy the code

As you can see, static code blocks and static variable assignments are the fastest to execute. They are executed in the order written in the class, followed by assignment of User’s member variables, User’s non-static code blocks, and finally the constructors. Normal code blocks are actually pretty much normal code.

Well, that’s all for today. Class is over.

















It’s a very complicated problem

Ah, hello, is it that simple? I am embarrassed to send out, the above topic almost learned Java can be done, come to come, add some difficulty, is not there is an inheritance, I add to you.

public class SonUser extends User { private static final Address address1=new Address("beijing"); private Address address2=new Address("nanjing"); Static {system.out.println ("-- SonUser static block 1--"); } {system.out.println ("-- SonUser non-static code block 1--"); } public SonUser(){{system.out.println ("-- SonUser common block 1--"); } system.out.println ("-- SonUser constructor --"); {system.out.println ("-- SonUser's normal block 2--"); }} {system.out.println ("-- SonUser non-static code block 2--"); } static {system.out.println ("-- SonUser static block 2--"); }}Copy the code
public class StaticCodeTest { public static void main(String[] args) { new SonUser(); }}Copy the code

This answer is a bit long. You don’t have to write the answer first. Let’s see.

-- type =guangdong -- User -- -- type =hubei -- User -- -- Address Type = Beijing -- SonUser static code block 1-- -- SonUser static code block 2-- -- Address: type =guangxi -- User non-static code block 1-- -- Address constructor :province=hunan -- User's non-static code block 2-- -- User's normal code block 1-- -- User's normal code block 2-- -- Address Type =nanjing -- SonUser's non-static code block 1-- -- SonUser's non-static code block 2-- -- SonUser's normal code block 1-- -- SonUser's constructor -- -- SonUser Normal block 2 for SonUserCopy the code

As you can see, static (both parent and subclass) are basically implemented at the beginning, static variables and static code blocks, but the superclass is executed faster than the subclass, and after the static code block is executed, the superclass variable is executed

Static variable assignment and static code block can be regarded as a package of static code, packaged together in code order, and member variable assignment non-static code block also in a package, the former we can call the static code package, the latter we can call the non-static code package.

Static code packages are executed when the class is loaded, this one only once; The non-static package is executed every time you declare (new) an object, and then the constructor is executed, notice that the non-static package is executed every time, and the constructor executes that constructor depending on which one is called.

Let’s look at Byte Code

I made up the names of the static and non-static packages here, but there is such a thing.

Let’s look at the bytecode of the User class.

public class test/other/entity/User { // compiled from: User.java // access flags 0x1A private final static Ltest/other/entity/Address; address1 // access flags 0x2 private Ltest/other/entity/Address; address2 // access flags 0x1A private final static Ltest/other/entity/Address; address3 // access flags 0x2 private Ltest/other/entity/Address; address4 // access flags 0x1 public <init>()V L0 LINENUMBER 25 L0 ALOAD 0 INVOKESPECIAL java/lang/Object.<init> ()V L1 LINENUMBER 10 L1 ALOAD 0 NEW test/other/entity/Address DUP LDC "guangxi" INVOKESPECIAL test/other/entity/Address.<init> (Ljava/lang/String;) V PUTFIELD test/other/entity/User.address2 : Ltest/other/entity/Address; L2 LINENUMBER 22 L2 GETSTATIC java/lang/System.out : Ljava/io/PrintStream; LDC "non-static code block 1 -- -- the User" INVOKEVIRTUAL Java/IO/PrintStream println (Ljava/lang/String;) V L3 LINENUMBER 36 L3 ALOAD 0 NEW test/other/entity/Address DUP LDC "hunan" INVOKESPECIAL test/other/entity/Address.<init> (Ljava/lang/String;) V PUTFIELD test/other/entity/User.address4 : Ltest/other/entity/Address; L4 LINENUMBER 39 L4 GETSTATIC java/lang/System.out : Ljava/io/PrintStream; LDC "- the User is not a static block 2 -" INVOKEVIRTUAL Java/IO/PrintStream println (Ljava/lang/String;) V L5 LINENUMBER 27 L5 GETSTATIC java/lang/System.out : Ljava/io/PrintStream; LDC "ordinary code block 1 -- -- the User" INVOKEVIRTUAL Java/IO/PrintStream println (Ljava/lang/String;) V L6 LINENUMBER 29 L6 GETSTATIC java/lang/System.out : Ljava/io/PrintStream; LDC "- the User constructor -" INVOKEVIRTUAL Java/IO/PrintStream println (Ljava/lang/String;) V L7 LINENUMBER 31 L7 GETSTATIC java/lang/System.out : Ljava/io/PrintStream; LDC "- the User common code block 2 -" INVOKEVIRTUAL Java/IO/PrintStream println (Ljava/lang/String;) V L8 LINENUMBER 33 L8 RETURN L9 LOCALVARIABLE this Ltest/other/entity/User; L0 L9 0 MAXSTACK = 4 MAXLOCALS = 1 // access flags 0x8 static <clinit>()V L0 LINENUMBER 9 L0 NEW test/other/entity/Address DUP LDC "guangdong" INVOKESPECIAL test/other/entity/Address.<init> (Ljava/lang/String;) V PUTSTATIC test/other/entity/User.address1 : Ltest/other/entity/Address; L1 LINENUMBER 18 L1 GETSTATIC java/lang/System.out : Ljava/io/PrintStream; LDC "- the User static block 1 -" INVOKEVIRTUAL Java/IO/PrintStream println (Ljava/lang/String;) V L2 LINENUMBER 35 L2 NEW test/other/entity/Address DUP LDC "hubei" INVOKESPECIAL test/other/entity/Address.<init> (Ljava/lang/String;) V PUTSTATIC test/other/entity/User.address3 : Ltest/other/entity/Address; L3 LINENUMBER 43 L3 GETSTATIC java/lang/System.out : Ljava/io/PrintStream; LDC "- the User static block 2 -" INVOKEVIRTUAL Java/IO/PrintStream println (Ljava/lang/String;) V L4 LINENUMBER 44 L4 RETURN MAXSTACK = 3 MAXLOCALS = 0 }Copy the code

Unicode was converted to Chinese by me.

The static code package is static

()V, and the non-static code block is public

()V. The Clinit method is the one that gets executed when the class is loaded into memory, and the init method is the one that gets called every time the constructor is called.

INVOKESPECIAL Java /lang/Object.

()V, well, this is the method that triggers the constructor of the parent class, Soga, so the subclass will call the constructor of the parent class, and then it will trigger the loading of the parent class, and then it will trigger the static code package of the parent class, The parent constructor triggers the parent constructor on the first line, which triggers the parent loading, which triggers the parent static package, which triggers the parent… If we loop through the Object class, we start executing the parent nonstatic code package, the parent nonstatic code package, the subclass nonstatic code package…

You can associate it with recursion.

I also wanted to put the parent constructor at the bottom, but I only saw the relentless popularity of IDEA and of course couldn’t implement it. If you don’t add super(), you default to the superclass constructor with an empty argument, super().

— — — — — — — — — — — — — — —

The more you know, the more you don’t know.

If you have any questions about the content of this article, please comment directly or email me. If you think my writing is good, a “like” is also a sign of support

Shall not be reproduced without permission!