面试官:小伙子来说一说Java中final关键字,以及它和finally、finalize()有什么区别?

简介: 面试官:“小伙子,用过final关键字吗?”我:“必须用过呀”面试官:“好,那来说一说你对这个关键字的理解吧,再说一说它与finally、finalize()的区别”我:“好嘞!

写在开头

面试官:“小伙子,用过final关键字吗?”
我:“必须用过呀”
面试官:“好,那来说一说你对这个关键字的理解吧,再说一说它与finally、finalize()的区别”
我:“好嘞!”

final中文释义:最终的,最后的;在Java中作为关键字的一种,被用来修饰变量、方法、类,final 语义是不可改变的。

final修饰变量

当final修饰变量时有如下几点需要注意:

1、final 修饰表示常量、一旦创建不可改变;
2、final 修饰的局部变量必须在声明时给定初值;
3、final 修饰的成员变量必须在声明时给定初值或者在构造方法内设置初始值,只能读取,不可修改;
4、被 final 修饰的成员变量必须要初始化,赋初值后不能再重新赋值(可以调用对象方法修改属性值)。
   对基本类型来说是其值不可变;对引用变量来说其引用不可变,即不能再指向其他的对象;

【代码示例】

public class Test {
   
   
    private String name;
    public final int age = 18;
    //和static一同修饰时,被当做常量
    private static final int HIGH = 180;

    public String getName() {
   
   
        return name;
    }
    public void setName(String name) {
   
   
        this.name = name;
    }
    public int getWeight(){
   
   
        final int weight;
        //修饰局部变量时,不能再赋值,需要在声明时给定初始值!
        return weight;
    }
    public static void main(String[] args) {
   
   
       final Test test = new Test();
       // 给一个被final修饰的引用类型重新赋值,编译器会报错,提示取消final修饰
       //test = new Test();
        // 但给这个引用类型进行属性赋值是可以的!
        test.setName("JavaBuild");
        //final修饰的成员变量,给定初始值后不可再修改,但可以调用
        if(test.age == 18){
   
   
            System.out.println("永远18岁");
        }
    }
}

final修饰方法

当final修饰方法时需要注意:

1、final修饰的方法:只能使用,不能被子类重写,但能够类内重载;

【代码示例】

public class Test extends Animal{
   
   
    //方法的重写不被允许
    public void run(){
   
       
    }
}
class Animal {
   
   
    public final void run(){
   
   
        System.out.println("我会跑");
    }
    //方法的重载,被允许
    public final void run(String dog){
   
   
        System.out.println("我会跑");
    }
}

image.png

final修饰类

当final修饰方法时需要注意:

1final修饰的类不能被继承,没有子类;
2final 类中的方法默认是 final 的,比如String类;

【代码示例】

public class Test extends Animal{
   
   

}
 final class Animal {
   
   
    public final void run(){
   
   
        System.out.println("我会跑");
    }
}

image.png

final、finally、finalize()三者的区别?

final

见上文

finally

finally 异常处理的一部分,它只能用在 try/catch 语句中,表示希望 finally 语句块中的代码最后一定被执行(存在一些情况导致 finally 语句块不会被执行,如 jvm 结束)
不被执行的情况:

  • 直接返回未执行到 try-finally 语句块
  • 抛出异常未执行到 try-finally 语句块
  • 系统退出未执行到 finally 语句块

【代码示例】

public static String test() {
   
   
    String str = null;
    int i = 0;
    if (i == 0) {
   
   
        return str;//直接返回未执行到finally语句块
    }
    try {
   
   
        System.out.println("try...");
        return str;
    } finally {
   
   
        System.out.println("finally...");
    }
}

public static String test2() {
   
   
    String str = null;
    int i = 0;
    i = i / 0;//抛出异常未执行到finally语句块
    try {
   
   
        System.out.println("try...");
        return str;
    } finally {
   
   
        System.out.println("finally...");
    }
}

public static String test3() {
   
   
    String str = null;
    try {
   
   
        System.out.println("try...");
        System.exit(0);//系统退出未执行到finally语句块
        return str;
    } finally {
   
   
        System.out.println("finally...");
    }
}

finalize()

finalize() 是在 java.lang.Object 里定义的,Object 的 finalize() 方法什么都不做,对象被回收时 finalize() 方法会被调用。Java 技术允许使用 finalize() 方法在垃圾收集器将对象从内存中清除出去之前做必要清理工作,在垃圾收集器删除对象之前被调用的。
一般情况下,此方法由JVM调用。特殊情况下,可重写 finalize() 方法,当对象被回收的时候释放一些资源,须调用 super.finalize() 。

目录
相关文章
|
4天前
|
存储 缓存 Oracle
Java I/O流面试之道
NIO的出现在于提高IO的速度,它相比传统的输入/输出流速度更快。NIO通过管道Channel和缓冲器Buffer来处理数据,可以把管道当成一个矿藏,缓冲器就是矿藏里的卡车。程序通过管道里的缓冲器进行数据交互,而不直接处理数据。程序要么从缓冲器获取数据,要么输入数据到缓冲器。
Java I/O流面试之道
|
1天前
|
存储 Java 程序员
Java基础的灵魂——Object类方法详解(社招面试不踩坑)
本文介绍了Java中`Object`类的几个重要方法,包括`toString`、`equals`、`hashCode`、`finalize`、`clone`、`getClass`、`notify`和`wait`。这些方法是面试中的常考点,掌握它们有助于理解Java对象的行为和实现多线程编程。作者通过具体示例和应用场景,详细解析了每个方法的作用和重写技巧,帮助读者更好地应对面试和技术开发。
19 4
|
5天前
|
Java
Java代码解释++i和i++的五个主要区别
本文介绍了前缀递增(++i)和后缀递增(i++)的区别。两者在独立语句中无差异,但在赋值表达式中,i++ 返回原值,++i 返回新值;在复杂表达式中计算顺序不同;在循环中虽结果相同但使用方式有别。最后通过 `Counter` 类模拟了两者的内部实现原理。
Java代码解释++i和i++的五个主要区别
|
14天前
|
存储 Java 程序员
Java面试加分点!一文读懂HashMap底层实现与扩容机制
本文详细解析了Java中经典的HashMap数据结构,包括其底层实现、扩容机制、put和查找过程、哈希函数以及JDK 1.7与1.8的差异。通过数组、链表和红黑树的组合,HashMap实现了高效的键值对存储与检索。文章还介绍了HashMap在不同版本中的优化,帮助读者更好地理解和应用这一重要工具。
33 5
|
13天前
|
存储 Java
[Java]面试官:你对异常处理了解多少,例如,finally中可以有return吗?
本文介绍了Java中`try...catch...finally`语句的使用细节及返回值问题,并探讨了JDK1.7引入的`try...with...resources`新特性,强调了异常处理机制及资源自动关闭的优势。
15 1
|
13天前
|
Java
通过Java代码解释成员变量(实例变量)和局部变量的区别
本文通过一个Java示例,详细解释了成员变量(实例变量)和局部变量的区别。成员变量属于类的一部分,每个对象有独立的副本;局部变量则在方法或代码块内部声明,作用范围仅限于此。示例代码展示了如何在类中声明和使用这两种变量。
|
22天前
|
Java 程序员
Java 面试高频考点:static 和 final 深度剖析
本文介绍了 Java 中的 `static` 和 `final` 关键字。`static` 修饰的属性和方法属于类而非对象,所有实例共享;`final` 用于变量、方法和类,确保其不可修改或继承。两者结合可用于定义常量。文章通过具体示例详细解析了它们的用法和应用场景。
22 3
|
11天前
|
算法 Java
JAVA 二叉树面试题
JAVA 二叉树面试题
12 0
|
16天前
|
Java
Java代码解释静态代理和动态代理的区别
### 静态代理与动态代理简介 **静态代理**:代理类在编译时已确定,目标对象和代理对象都实现同一接口。代理类包含对目标对象的引用,并在调用方法时添加额外操作。 **动态代理**:利用Java反射机制在运行时生成代理类,更加灵活。通过`Proxy`类和`InvocationHandler`接口实现,无需提前知道接口的具体实现细节。 示例代码展示了两种代理方式的实现,静态代理需要手动创建代理对象,而动态代理通过反射机制自动创建。
|
18天前
|
缓存 算法 Java
Java 中线程和纤程Fiber的区别是什么?
【10月更文挑战第14天】
45 0