【Java基础】static关键字详解

本文详细介绍了Java中的static关键字,包括其修饰变量、方法和类的作用。static变量存储在元空间,初始化时类加载。静态方法不能访问非静态成员,因为它们在不同的内存区域。同时,文章通过示例展示了静态代码块的执行顺序,强调了静态成员在类加载时初始化,而非静态成员在对象创建时初始化。
摘要由CSDN通过智能技术生成

static关键字详解

结论

先上结论,一会我们用实例讲解。

  • static关键字表示静态的,可以修饰变量、方法、类,还可以实现静态代码块。
  • 静态变量统一存储在元空间中(在JDK1.8之后,1.7是方法区),具体可以看JVM内存详解。
  • 如果一个字段是静态的基本类型,你没有初始化它,那么它就会获得基本类型的标准初值。如果它是对象引用,那么它的默认初值就是 null。(摘自《On Java8》)

static修饰变量及方法

首先由static修饰的变量是静态成员变量,它是属于类的,所以可以直接使用类名去访问。

static变量在内存中独占一份,在类初次加载时才会进行初始化。

而static方法同理,由下图所示:

static代码展示
在图片中我们可以看到,类名可以直接对静态成员变量和方法访问,但是对非静态进行引用会有爆红提示,这是因为在静态方法内部,不允许引用非静态成员与方法。具体原因下一节进行讲解。

static与JVM的关系

下面先给出Java虚拟机经典的内存模型。
JVM内存模型
static变量与方法都存储在MetaSPACE(在JDK1.7前是叫做方法区)中,而普通变量存储在堆区中,那么JVM对类进行加载是一个怎样的步骤呢?

我们引用《深入理解JVM》这本书的讲解,可以知道类的加载过程。
类加载过程

而我们由static修饰的所有东西都在准备阶段进行初始化,而非静态的是在类实例化为对象阶段才会进行初始化,注意不要混淆实例化和加载

所以我们可以解释上一节的问题,静态函数中不可以访问非静态成员。

static静态代码块和初始化顺序

static除了修饰变量、函数,还可以使用静态代码块,可以使我们有些代码启动即执行,下面有这样一个例子。

public class Father {

    static {
        System.out.println("父类静态代码块");
    }

    {
        System.out.println("父类代码块");
    }

    public Father() {
        System.out.println("父类构造函数");
    }
}

class Son extends Father{

    static {
        System.out.println("子类静态代码块");
    }

    {
        System.out.println("子类代码块");
    }

    public Son() {
        System.out.println("子类代码块");
    }

    public static void main(String[] args) {
        Son son = new Son();
    }
}

答案如下:

父类静态代码块
子类静态代码块
父类代码块
父类构造函数
子类代码块
子类代码块

总结来说,静态代码总是优先执行,之后就是父类优先于子类。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值