1.概念
代码块又叫初始化块,属于类中的成员(是类的一部分),类似于方法,将逻辑语句封装到方法体中,通过{ }包围。与方法不同,代码块没有方法名,没有返回,没有参数,只有方法体,而且不用通过对象或者类显式调用,而是加载类时、或创建类时隐形调用。
2.注意事项
(1) 代码块何时执行
static修饰的代码块,也叫静态代码块,作用是对类进行初始化,而且它随着类的加载而执行,并且只会执行一次。如果是普通的代码块,每创建一个对象,就执行一次。
(2)何时进行类加载
1.创建对象实例(new);
2.创建子类对象实例时,父类也会被加载;
3.使用类的静态成员时(静态属性,静态方法);
如果只是涉及到使用类的静态成员,普通代码块不会执行(因为没有创建对象)。
public class CodeBlock02 {
public static void main(String[] args) {
//创建对象,类被加载,执行静态代码块
//创建对象,执行普通代码块
A2 a1 = new A2();
//第二次创建对象,不用加载类,只执行普通代码块
A2 a2 = new A2();
}
}
class A2{
static{
System.out.println("这是一个静态代码块");
}
{
System.out.println("这是一个普通代码块");
}
}
(3)创建一个对象时,在一个类中的调用顺序
1.调用静态代码块和静态属性的初始化。这两个的优先级一样,如果有多个静态代码块和多个静态变量初始化,按定义顺序调用。
2.调用普通代码块和普通属性的初始化。这两个的优先级一样,如果有多个普通代码块和多个普通变量初始化,按定义顺序调用。
3.调用构造器
public class CodeBlockDetail02 {
public static void main(String[] args) {
A a = new A();
}
}
class A{
private int n2=getN2();//普通属性的初始化
{//普通代码块
System.out.println("A 普通代码块01");
}
static {//静态的代码块
System.out.println("A 静态代码块01");
}
//静态属性的初始化
public static int n1=getN1();
public static int getN1(){
System.out.println("getN1被调用....");
return 100;
}
public int getN2(){//普通方法 非静态
System.out.println("getN2被调用...");
return 200;
}
public A(){
System.out.println("A 构造器被调用");
}
}
(4)构造器前面隐含了super()和调用普通代码块
静态代码块和静态属性初始化在类加载时,就执行完毕,因此优先于构造器和普通代码块的执行。
3.父子类继承的执行顺序
1.父类的静态代码块和静态属性初始化,二者优先级一样,按照代码书写先后顺序执行。
2.子类的普通代码块和普通属性初始化,二者优先级一样,按照代码书写先后顺序执行。
3.父类的构造器
4.子类的普通代码块和普通属性初始化二者优先级一样,按照代码书写先后顺序执行。
5.子类的构造器。
package com.hspedu.codeblock_;
public class CodeBlockDetails04 {
public static void main(String[] args) {
//(1).进行类的加载
//先加载父类A02,再加载B02
//(2)创建类对象
//1.从子类的构造器开始
new B02();
}
}
class A02{
private static int n1=getVal01();
static {
System.out.println("A02的一个静态代码块...");//2>.
}
{
System.out.println("A02的一个普通代码块...");//5>.
}
public int n3=getVal02();//6>.
public static int getVal01() {
System.out.println("getVal01");//1>.
return 10;
}
public int getVal02() {
System.out.println("getVal02");//6>.
return 10;
}
public A02(){
//隐藏
//super()
//普通代码块和普通属性的初始化...
System.out.println("A02的构造器");//7>.
}
}
class B02 extends A02{
private static int n3=getVal03();
static {
System.out.println("B02的一个静态代码块");//4>.
}
public int n5=getVal04();//8>.
{
System.out.println("B02的第一个不同代码块");//9>.
}
public static int getVal03(){
System.out.println("getVal03");//3>.
return 10;
}
public int getVal04(){
System.out.println("getVal04");//8>.
return 10;
}
public B02(){
//隐藏
//super()
//普通代码块和普通属性的初始化...
System.out.println("B02的构造器");//10>.
System.out.println("B02的构造器");//11>.
}
}
!!!静态代码块中只能直接调用惊天成员(静态属性和静态方法),普通代码块中可以调用任意成员。