# 六、final

# 1. 不变性

如果对象在被创建后,状态就不能被修改,那么它就是不可变的。

  • 对于不可变对象,一定是线程安全的。

# 2. final 的作用

  • 类防止被继承
  • 方法防止被重写
  • 变量防止被修改
  • 天生线程安全

# 3. final 三种用法

# 3.1 修饰变量

  • 被 final 修饰的变量,意味着值不能被修改。如果变量是对象,那么对象的引用不能变,但是对象自身的内容依然可以变化

# ① final instance variable(类中的 final 属性)

赋值时机:

  • 声明变量时等号右边直接赋值
  • 构造函数中赋值
  • 初始化代码块中赋值
  • 不能不赋值

# ② final static variable(类中的 static final 属性)

赋值时机:

  • 声明变量时直接等号赋值
  • static 静态代码块赋值
  • 不可用普通初始代码块赋值

# ③ final local variable(方法中的 final 变量)

赋值时机:

  • 使用变量前必须先赋值
# 为什么要规定赋值时机?
1. 不赋值的话默认就是 null 了,又因为 final,后面又改变不了了,就只能是 null 了。

# 3.2 修饰方法

  • 构造方法不允许 final 修饰。
  • 不可被重写(static 也是,static 不是重写,而是毫无关系)。

# 3.3 修饰类

  • 不可被继承(如 String)。

# 4. 注意点

  • 被 final 修饰的变量,意味着值不能被修改。如果变量是对象,那么对象的引用不能变,但是对象自身的内容依然可以变化
  • 明确知道不可变就加 final。
  • final 修饰 String 的话,如果编译器可以判断它是值,那么会直接放到常量池当中。

# 5. 不变性和 final 的关系

不变性并不意味着简单使用 final 修饰就是不可变

  • 对于基本数据类型,确实被 final 修饰后就具有不变性
  • 但是对于对象类型,需要该对象保证自身被创建后,状态永远不会变才可以。
  • 一个 final 对象必须里面所有的属性都是 final 的这个对象才是不可变的。

# 6. 栈封闭

在方法里面新建的局部变量,实际上是存储在每个线程私有的栈空间,而每个栈的栈空间是不能被其他线程所访问到的,所以不会有线程安全问题。这就是“栈封闭”技术,是“线程封闭”技术的一种情况。

上次更新: 11/1/2021, 10:07:49 AM