Java(十八)——final修饰符

本文详细介绍了final关键字在Java中的使用,包括final修饰成员变量、局部变量、方法和类的不同方式及含义,并探讨了如何利用final创建不可变类以及缓存实例。

final关键字可用于修饰类、变量和方法,用于表示它修饰的类、方法和变量不可改变。

final修饰变量时,表示该变量一旦获得了初始值就不可被改变,final既可以修饰成员变量(包括类变量和实例变量),也可以修饰局部变量、形参。由于final变量获得初始值之后就不能被重新赋值,因此final修饰成员变量和修饰局部变量有一定的不同。

一、final成员变量

final修饰类变量、实例变量能指定初始值的地方如下。

  • 类变量:必须在静态初始化块中指定初始值或声明该类变量时指定初始值,而且只能在两个地方的其中之一指定。
  • 实例变量:必须在非静态初始化块、声明该实例变量或构造器中指定初始值,而且只能在三个地方的其中之一指定。

Java语法规定:final修饰的成员变量必须由程序员显式地指定初始值。

二、final局部变量

系统不会对局部变量进行初始化,局部变量必须由程序员显式初始化。因此使用final修饰局部变量时,既可以在定义时指定默认值,也可以后面代码中对该final变量赋初始值。

三、final修饰基本类型变量和引用类型变量的区别

当使用final修饰基本类型变量时,不能对基本类型变量重新赋值,因此基本类型变量不能被改变。但对于引用类型变量而言,它保存的仅仅是一个引用,final只保证这个引用类型变量所引用的地址不会改变,即一直引用同一个对象,但这个对象完全可以发生改变。

四、可执行“宏替换”的final变量

对一个final变量来说,不管它是类变量、实例变量,还是局部变量,只要满足三个条件,这个final变量就不再是一个变量,而是相当于一个直接量。

  • 使用final修饰符修饰。
  • 在定义该final变量时指定了初始值。
  • 该初始值可以在编译时就被确定下来。

final修饰符的一个重要用途就是定义“宏变量”。满足上面三个条件,那么这个final变量本质上就是一个“宏变量”,编译器会把程序中所有用到该变量的地方直接替换成该变量的值。

五、final方法

final修饰的方法不可被重写。例如Java提供的Object类里就有一个final方法:getClass()。

六、final类

final修饰的类不可以有子类,例如java.lang.Math类就是一个final类,不可以有子类。

七、不可变类

不可变(immutable)类的意思是创建该类的实例后,该实例的实例变量是不可改变的。Java提供的8个包装类和java.lang.String类都是不可变类。

如果需要创建自定义的不可变类,可遵守如下规则:

  • 使用private和final修饰符来修饰该类的成员变量。
  • 提供带参数的构造器,用于根据传入参数来初始化类里的成员变量。
  • 仅为该类的成员变量提供getter方法,不提供setter方法,因为普通方法无法修改final修饰的成员变量。
  • 如果有必要,重写Object类的hasCode()和equals()方法。equals()方法根据关键成员变量来作为两个对象是否相等的标准,除此之外,还应该保证两个用equals()方法判断为相等的对象的hashCode()也相等

如果需要设计一个不可变类,尤其要注意其引用类型的成员变量,如果引用类型的成员变量的类是可变的,就必须采取必要的措施来保护该成员变量所引用的对象不会被修改,这样才能创建真正的不可变类。

八、缓存实例的不可变类

不可变类的实例状态不可改变,可以很方便地被多个对象所共享。如果程序经常需要使用相同的不可变实例,则应该考虑缓存这种不可变类的实例。毕竟重复创建相同对象没有太大的意义,而且加大系统开销。如果可能,应该将已经创建的不可变类的实例进行缓存。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值