java中static和const和final的区别及使用说明

 更新时间:2026年08月12日 11:04:27   作者:华东设计之美  
还在为Java中的static、final和const关键字头疼吗?本文用大白话讲清它们的定义、用法、编译时机和内存存储位置,帮你彻底搞懂静态成员、常量以及为什么Java不用const,干货满满,快来学习吧

static关键字

static 关键字用于声明类的成员(方法或变量)为静态成员。静态成员属于类本身,而不是类的实例。

换句话说,静态成员可以通过类名直接访问,而不需要实例化对象。

  • 静态变量:属于类的所有对象共享,类的所有实例共享相同的内存位置。
  • 静态方法:可以在没有创建对象的情况下直接调用。
  • 静态块:在类加载时执行一次,用于初始化类的静态成员。
  • 编译时机static 关键字主要在编译时确定。它告诉 JVM,该成员属于类而非实例,因此不需要通过对象来访问。static 修饰的变量和方法会被加载到 方法区 中的 类的结构部分
  • 内存存储位置static 成员存储在 方法区 中的 类的静态变量区。每个类只有一个静态变量区,所有实例共享这部分内存。静态方法也存储在方法区的 方法区(Method Area) 中。

count 是静态变量,在两个 Counter 对象中共享,displayCount 是静态方法,可以通过类名直接调用。

class Counter {
    static int count = 0;  // 静态变量
    
    Counter() {
        count++;  // 每次创建对象时,静态变量 count 会增加
    }

    static void displayCount() {
        System.out.println("Count: " + count);  // 静态方法可以直接访问静态变量
    }
}

public class Main {
    public static void main(String[] args) {
        Counter c1 = new Counter();
        Counter c2 = new Counter();
        Counter.displayCount();  // 调用静态方法,输出 Count: 2
    }
}

final关键字

final 是一个多用途的关键字,它可以用于变量、方法和类的定义,分别具有不同的含义。

  • 用于变量:声明为 final 的变量是常量,一旦赋值后不可更改(不可重新赋值)。
  • 用于方法:声明为 final 的方法不能被子类重写。
  • 用于类:声明为 final 的类不能被继承。
  • 编译时机final 关键字的使用在编译时就确定了变量、方法或类的行为。例如,如果一个方法被声明为 final,编译器会禁止任何子类重写该方法;如果一个类被声明为 final,编译器会禁止任何子类继承该类。对于变量,final 确保该变量一旦赋值后不可修改。

内存存储位置

  • final 变量:常量(final 变量)通常在 方法区 中的 常量池(Constant Pool) 中存储。如果是局部变量,存储在栈中。
  • final 类和方法:存储在 方法区 中的 类的结构部分final 类和方法不会被继承或重写,因此它们在运行时不需要动态解析。

PI 被声明为 final,因此它的值不能更改。

// final 变量
class Circle {
    final double PI = 3.14159;  // 常量,值不可更改
    
    void calculateArea(double radius) {
        double area = PI * radius * radius;  // 使用常量
        System.out.println("Area: " + area);
    }
}

public class Main {
    public static void main(String[] args) {
        Circle circle = new Circle();
        circle.calculateArea(5);
        // PI = 3.14;  // 编译错误,无法修改 final 变量的值
    }
}

const关键字

在 Java 中,const 是一个保留关键字,但它并没有在语言中实现功能,实际上 Java 中并不使用 const 来定义常量。Java 提供了 final 来替代 const 的功能。

  • const 在 Java 中没有实现任何功能。
  • const 关键字保留用于未来可能的用途,但目前不被使用。
  • 常量在 Java 中应该使用 final 关键字来定义。
  • 编译时机:虽然 const 是 Java 中的保留关键字,但它并没有被实现。实际上,Java 没有使用 const 来定义常量。在 Java 中,我们通常使用 final 来定义常量。
  • 内存存储位置:由于 const 不被实际使用,它不会在内存中占用任何空间。任何常量都应该使用 final 来定义,并存储在 方法区的常量池 或堆栈中。

使用 const 会导致编译错误,因为 const 在 Java 中并没有实际作用。 

// const 在 Java 中并不使用
public class Main {
    public static void main(String[] args) {
        // const int x = 10;  // 编译错误,const 不被使用
    }
}
特性staticfinalconst
定义用于类的成员(方法、变量)指定该成员为静态的用于变量、方法、类,表示常量、不允许修改或重写目前在 Java 中没有实现
使用场景当需要共享数据或功能时使用用于常量、禁止继承/重写的方法、不可修改的变量Java 中不使用 const
作用域静态成员属于类,而不是实例对象变量不可修改,方法不可重写,类不可继承不被使用
示例static int count;final int x = 10;不支持
静态方法静态方法可以在没有实例化对象的情况下直接调用不适用不适用
继承/重写静态成员可以被继承,但不可以被重写final 方法不能被重写,final 类不能被继承不适用
关键字编译时机内存存储位置说明
static编译时方法区 中的 类的静态变量区,静态方法也存储在方法区中static 成员属于类而非实例,所有实例共享这部分内存
final编译时方法区的常量池 或 堆栈(针对局部变量)final 变量会存储在常量池中,final 方法和类存储在方法区
const编译时不会被使用const 是保留关键字,Java 没有实际应用,通常用 final 代替

完整示例

class Person {
    static String species = "Homo sapiens";  // 静态变量
    final String name;  // 常量,必须在构造方法中初始化

    Person(String name) {
        this.name = name;
    }

    // final 方法,不能被子类重写
    final void showDetails() {
        System.out.println("Name: " + name + ", Species: " + species);
    }
}

class Student extends Person {
    Student(String name) {
        super(name);
    }

    // 编译错误,无法重写 final 方法
    // void showDetails() { 
    //     System.out.println("Student: " + name);
    // }
}

public class Main {
    public static void main(String[] args) {
        Person person = new Person("Alice");
        person.showDetails();  // 调用父类的 final 方法
        
        // 通过类名访问静态变量
        System.out.println("Species: " + Person.species);

        // 修改静态变量
        Person.species = "Homo erectus";
        System.out.println("Updated Species: " + Person.species);

        // name = "Bob";  // 编译错误,final 变量不可修改
    }
}

Java 内存区的详细说明

1.方法区(Method Area)

  • 存放内容:类的结构(包括类的元数据)、静态变量、常量池、方法代码等。
  • 静态成员和常量static 成员变量和 final 常量通常存储在方法区中。静态方法也存储在方法区。常量则会存放在类的常量池(Constant Pool)中。

2.堆(Heap)

  • 存放内容:对象实例、数组、类的实例等。
  • final 变量(如果是对象引用):如果 final 变量是引用类型,则它的引用会存放在栈中,但对象本身会存放在堆中。

3.栈(Stack)

  • 存放内容:局部变量、方法调用信息、操作数栈等。
  • final 局部变量:局部变量(如方法参数)如果是 final,则存储在栈上。

4.程序计数器(Program Counter Register)

  • 存放内容:每个线程都有一个程序计数器,指向当前执行的字节码指令。
  • final 修饰的局部变量(参数):存储在栈上,而栈本身不直接与程序计数器相关联。

5.本地方法栈(Native Method Stack)

  • 存放内容:存放 native 方法的调用信息。

总结

以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。

相关文章

  • Java跨session实现token接口测试过程图解

    Java跨session实现token接口测试过程图解

    这篇文章主要介绍了Java跨session实现token接口测试过程图解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2020-04-04
  • 详解springMVC获取前端请求的数据与三个作用域

    详解springMVC获取前端请求的数据与三个作用域

    文章介绍了Spring MVC中获取前端请求数据的多种方式,包括使用@RequestParam注解、@RequestHeader注解和@CookieValue注解,以及处理请求中文乱码的方法,本文通过实例代码给大家介绍的非常详细,感兴趣的朋友跟随小编一起看看吧
    2026-02-02
  • Mybatis-Plus中的MetaObjectHandler组件的使用

    Mybatis-Plus中的MetaObjectHandler组件的使用

    MetaObjectHandler是Mybatis-Plus中一个实用组件,专门用于自动处理实体对象中的特定字段,如创建时间、更新时间、创建人和修改人等,该接口允许开发者在不修改业务代码的情况下,实现自动填充功能,极大地简化了代码的复杂性,感兴趣的可以了解一下
    2024-10-10
  • Java设计模式之工厂模式实现方法详解

    Java设计模式之工厂模式实现方法详解

    这篇文章主要介绍了Java设计模式之工厂模式实现方法,结合实例形式较为详细的分析了工厂模式的分类、原理、实现方法与相关注意事项,需要的朋友可以参考下
    2017-12-12
  • Spring Cloud下OAUTH2注销的实现示例

    Spring Cloud下OAUTH2注销的实现示例

    本篇文章主要介绍了Spring Cloud下OAUTH2注销的实现示例,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2018-03-03
  • 巧用FutureTask 线程池轻松解决接口超时问题

    巧用FutureTask 线程池轻松解决接口超时问题

    这篇文章主要为大家介绍了使用FutureTask结合线程池轻松解决接口超时问题的巧妙用法,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-11-11
  • Java WebSocket客户端接收大量数据的三种方案

    Java WebSocket客户端接收大量数据的三种方案

    WebSocket是一种基于TCP协议的全双工通信协议,它能够在客户端和服务器之间建立一个持久连接,实现实时的双向数据传输,在实际应用中,有时候我们需要处理大量的数据,所以本文将介绍如何使用 Java WebSocket 客户端接收大量数据,并提供一些优化方案
    2023-11-11
  • Java Assert.assertEquals案例详解

    Java Assert.assertEquals案例详解

    这篇文章主要介绍了Java Assert.assertEquals案例详解,本篇文章通过简要的案例,讲解了该项技术的了解与使用,以下就是详细内容,需要的朋友可以参考下
    2021-08-08
  • springboot乱码问题排查思路解析

    springboot乱码问题排查思路解析

    这篇文章主要为大家介绍了springboot乱码问题排查思路解析,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-06-06
  • SpringBoot2 Jpa 批量删除功能的实现

    SpringBoot2 Jpa 批量删除功能的实现

    这篇文章主要介绍了SpringBoot2 Jpa 批量删除功能的实现,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2021-01-01

最新评论