小议Java中final关键字使用时的注意点_java

final 类
final 类不能被继承,同时,一旦用 final 修饰了类,也就意味着 final 类中的所有方法都被隐式地指定为 final 方法

final 方法
在类继承的过程中,对于父类中的 final 方法,子类不能修改和覆盖。
private 方法都被隐式指定为 final 方法。
有两个原因使用 final 方法:

  • 锁定方法,防止被子类修改其含义
  • 在早期的 java 实现版本中,final 方法被实现为内嵌调用,可以提升性能

final 变量
final 关键字用来修饰变量是最常用的用法,如果修饰成员变量,则必须在定义时或者构造方法中初始化,且一经初始化此后不能再进行任何赋值。
针对基本类型和类对象有着不同的含义:

  • 对于基本类型,final 变量一经初始化,此后不能再改变该变量的值
  • 对于类对象,已经初始化后,不能让这个变量再指向另一个对象,但他指向的对象的内容是可以改变的

static final 域称为编译期常量,一般全部大写。

示例

class Glyph {
 void draw() {
  System.out.println("Glyph.draw()");
 }
 Glyph() {
  System.out.println("Glyph() before draw()");
  draw();
  System.out.println("Glyph() after draw()");
 }
}
class RoundGlyph extends Glyph {
 private int redius = 1;
 RoundGlyph(int r) {
  radius = r;
  System.out.println("RoundGlyph.RoundGlyph(), radius = " + radius);
 }
 void draw() {
  System.out.println("RoundGlyph.draw(), radius = " + radius);
 }
}
public class RolyConstructors {
 public static void main(String[] args) {
  new RoundGlyph(5);
 }
}

输出结果:

Glyph() before draw()
RoundGlyph.draw(), radius = 0
Glyph() after draw()
RoundGlyph.RoundGlyph(), radius = 5

上面的代码展示了类初始化过程以及隐藏的灾难性问题。
main 函数中以参数 5 调用 RoundGlyph 的构造函数创建了 RoundGlyph 对象,在 RoundGlyph 构造方法执行前调用了其父类 Glyph 的构造方法。
然而,在父类 Glyph 的构造方法中调用了 draw 方法,由于多态性,此时实际上调用了子类的 draw 方法,然而子类的 redius 此时还没有通过构造器初始化,因此输出了:

RoundGlyph.draw(), radius = 0

这显然不是我们想要的结果,因此需要注意:

  • 用尽可能简单的方法初始化类成员
  • 在构造器中最好只调用 final 方法

第二条的原因是 final 不会应用多态性,因此可以保证调用的是当前对象的相应方法,而不是初始化工作还没有进行的子类的覆盖方法。

总结final的内存分配方式:
1.修饰变量:
通常情况下,final变量有3个地方可以赋值:直接赋值,构造函数中,或是初始化块中。
(1)初始化:
由于在java的语法中,声明和初始化是联系在一起的,
也就是说:如果你不显示的初始化一个变量,系统会自动用一个默认值来对其进行初始化。(如int就是0)
对于final变量,在声明时,如果你没有赋值,系统默认这是一个空白域,在构造函数进行初始化,
如果是静态的,则可以在初始化块。
(2)内存:
常量(final变量)和非final变量的处理方式是不一样的。
每一个类型在用到一个常量时,都会复制一份到自己的常量池中。
常量也像类变量(static)一样保存在方法区,只不过他保存在常量池。
(可能是,类变量被所有实例共享,而常量池是每个实例独有的。)
2.修饰方法:
保存在方法区,并且可以被函数代码直接替换,而不用等到执行时再决定具体是那个函数。
3.修饰类:
保存在方法区。

以上是小编为您精心准备的的内容,在的博客、问答、公众号、人物、课程等栏目也有的相关内容,欢迎继续使用右上角搜索按钮进行搜索java
final
java final关键字、android final关键字、final关键字、final关键字的作用、c final关键字,以便于您获取更多的相关知识。

时间: 2024-10-07 23:52:56

小议Java中final关键字使用时的注意点_java的相关文章

Java中final关键字的使用教程

final 具有"不可改变的"的含义,可以修饰 非抽象类.非抽象成员方法和变量.     用 final 修饰的类不能被继承,没有子类.    用 final 修饰的方法不能被子类的方法覆盖(重写).    用 final 修饰的变量表示常量,只能被赋一次值(声明变量的时候). 注: final 不能用来修饰构造方法,因为"方法覆盖"这一概念仅适用于类的成员方法,而不适用于类的构造方法,父类的构造方法和子类的构造方法之间不存在覆盖的关系,因此用final修饰构造方法

Java中final关键字详解_php技巧

谈到final关键字,想必很多人都不陌生,在使用匿名内部类的时候可能会经常用到final关键字.另外,Java中的String类就是一个final类,那么今天我们就来了解final这个关键字的用法. 主要介绍:一.final关键字的基本用法.二.深入理解final关键字 一.final关键字的基本用法 在Java中,final关键字可以用来修饰类.方法和变量(包括成员变量和局部变量).下面就从这三个方面来了解一下final关键字的基本用法. 1.修饰类 当用final修饰一个类时,表明这个类不能

Java中final关键字的用法总结_java

1.final修饰类被final修饰的类不能被继承,因此final类的成员方法也不能被覆写,被final关键字修饰的类没有子类,因此类的实现细节也无法改变,无法被扩展.final类中的所有成员方法都会被隐式地指定为final方法,final类中的成员变量可以根据需要设为final. 2.final修饰方法一个类中的方法如果被final关键字修饰,则其子类无法覆写该方法,只能被子类继承.如果父类中的某个方法不想被其子类所覆写,可将该方法定义为final类型,另外,父类中的私有方法(即被privat

Java面向对象编程中final关键字的使用方法详解_java

在Java中通过final关键字来声明对象具有不变性(immutable),这里的对象包括变量,方法,类,与C++中的const关键字效果类似. immutable指对象在创建之后,状态无法被改变 可以从三个角度考虑使用final关键字: 代码本身:不希望final描述的对象所表现的含义被改变 安全:final对象具有只读属性,是线程安全的 效率:无法修改final对象本身,对其引用的操作更为高效 final 变量定义final Object a,则a只能被初始化一次,一旦初始化,a的数据无法修

小议Java中@param注解与@see注解的作用_java

@ param@ param标签可以归档方法或构造器的某个单一参数,或者归档类.接口以及泛型方法的类型参数.在使用@ param标签时,我们应该针对方法的每一个参数都使用一个该标签.每个段落的第一个词会被当作参数名,而余下的部分则会被当作是对它的描述: @param max The maximum number of words to read. 当归档类型参数时,我们应该在类型参数名两边加上<和>: @param一e element type of this List 然而,类型参数通常并不

Java 中的关键字 final

final 根据程序上下文环境,Java关键字final有"这是无法改变的"或者"终态的"含义,它可以修 饰非抽象类.非抽象类成员方法和变量.你可能出于两种理解而需要阻止改变:设计或效率. final类不 能被继承,没有子类,final类中的方法默认是final的. final方法不能被子类的方法覆盖,但可以被继 承. final成员变量表示常量,只能被赋值一次,赋值后值不再改变. final不能用于修饰构造方法. 注意:父类的private成员方法是不能被子类方法

javase-JAVA中final关键字在不同位置的区别

问题描述 JAVA中final关键字在不同位置的区别 public void method1(final Object obj) { new AnonymousClass() { obj.invoke(); } } 与 public void method1(Object obj) { final Object tmpObj = obj; new AnonymousClass() { tmpObj .invoke(); } } 之间有区别吗?主要的区别是什么? 解决方案 final修饰变量意思这

详解Java中native关键字_java

 一. 什么是Native Method   简单地讲,一个Native Method就是一个java调用非java代码的接口.一个Native Method是这样一个java的方法:该方法的实现由非java语言实现,比如C.这个特征并非java所特有,很多其它的编程语言都有这一机制,比如在C++中,你可以用extern "C"告知C++编译器去调用一个C的函数.    "A native method is a Java method whose implementatio

java中final的用法

许多程序设计语言都有自己的办法告诉编译器某个数据是"常数".常数主要应用于下述两个方面: (1) 编译期常数,它永远不会改变 (2) 在运行期初始化的一个值,我们不希望它发生变化 对于编译期的常数,编译器(程序)可将常数值"封装"到需要的计算过程里.也就是说,计算可在编译期间提前执行,从而节省运行时的一些开销.在Java中,这些形式的常数必须属于基本数据类型(Primitives),而且要用final关键字进行表达.在对这样的一个常数进行定义的时候,必须给出一个值.