final关键字的一些思考
2017-11-27 11:51
344 查看
final关键字在面试时是一个非常频繁的问题,对它的理解一定程度上可以反应出面试者的基础和对技术的钻研能力,下面从基础使用到底层虚拟机来看一下final的相关内容。
1.final修饰的class(类)不能被继承;
2.final修饰的方法不能被重写,String就是被final修饰的;
3.被final修饰的变量不可以被改变(重点)
此处变量需要根据引用分类:
形如final a = 12引用不可变值,这种不必多说,不可变
形如 final Object a = new Object()引用对象
对象里面的内容可以改变,但是引用指向的地址不能被改变
1、被final修饰的方法,JVM会尝试为之寻求内联,这对于提升Java的效率是非常重要的。因此,假如能确定方法不会被继承,那么尽量将方法定义为final的。
内联后却少了保护现场、恢复线程、建立栈帧等一系列的工作
java语言因为多态的原因,只有在运行期间根据实际需要决定使用哪个实际的子类,这样非常灵活,但是这样导致在编译期间无法内联,因为不知道使用哪个方法,final关键字修饰的方法无法被重写,所以运行期间使用的方法在编译时必然是可以内联的。
2、被final修饰的常量,在编译阶段会存入调用类的常量池中,与实际定义这个常量的类没有关系
1.final修饰的class(类)不能被继承;
2.final修饰的方法不能被重写,String就是被final修饰的;
3.被final修饰的变量不可以被改变(重点)
此处变量需要根据引用分类:
形如final a = 12引用不可变值,这种不必多说,不可变
final int a = 12; a = 13;//此处报错:“The final local variable fs cannot be assigned”。
形如 final Object a = new Object()引用对象
package com.xue; public class FinalString { private String finStr; public FinalString(String finStr) { this.finStr = finStr; } public void setFinStr(String finStr) { this.finStr = finStr; } public String getFinStr() { return finStr; } @Override public String toString() { return super.toString(); } }
final FinalString s = new FinalString("12"); final FinalString ss = new FinalString("aaa"); s = ss;//此处报错:“The final local variable fs cannot be assigned”。 s.setFinStr("123"); System.out.println(s.getFinStr());//正确输出
对象里面的内容可以改变,但是引用指向的地址不能被改变
System.out.println(s.hashCode());//1 s.setFinStr("123"); System.out.println(s.hashCode());//和第一行输出时一样的,地址相同 System.out.println(ss.hashCode());
/** * final 修饰数组 * 用final修饰数组是没有意义的 */ String[] str1 = {"123", "234"}; final String[] str2 = {"345", "456"}; str1 = str2;//把Str2的内容赋给Str1也就是地址改变 System.out.println(str1.hashCode()); System.out.println(str2.hashCode()); str1[1] = "aaa"; System.out.println(str1.hashCode());
1、被final修饰的方法,JVM会尝试为之寻求内联,这对于提升Java的效率是非常重要的。因此,假如能确定方法不会被继承,那么尽量将方法定义为final的。
public final int getA() { getA()语句1; getA()语句2; getA()语句3; getA()语句4; getA()语句5 }
public static void main(String[] args) { main语句1; main语句2; int i = getA(); main语句3; main语句4 }
内联后却少了保护现场、恢复线程、建立栈帧等一系列的工作
public static void main(String[] args) { main语句1; main语句2; getA()语句1; getA()语句2; getA()语句3; getA()语句4; getA()语句5; main语句3; main语句4 }
java语言因为多态的原因,只有在运行期间根据实际需要决定使用哪个实际的子类,这样非常灵活,但是这样导致在编译期间无法内联,因为不知道使用哪个方法,final关键字修饰的方法无法被重写,所以运行期间使用的方法在编译时必然是可以内联的。
2、被final修饰的常量,在编译阶段会存入调用类的常量池中,与实际定义这个常量的类没有关系
public class ConstClass { public static final String HELLOWORLD = "Hello World"; static { System.out.println("ConstCLass init"); } } public class TestMain { public static void main(String[] args) { System.out.println(ConstClass.HELLOWORLD); } }
相关文章推荐
- final关键字和成员变量,构造方法,成员方法在继承的深入思考
- [转]构造函数为什么不能被abstract/static/final/native/stricftp/synchronized修饰 及 一些关键字的用法
- 关于final字段修饰静态变量的一些思考
- 尚硅谷程序-java 封装登陆程序 1-2static 的一些相关应用 2-2代码块 3-1final关键字
- 根据海子blog经过手动验证思考的 final关键字总结
- 对STM32 HAL库的一些思考(二)__weak关键字和systick
- volatile的关键字的一些思考
- tij学习笔记(static,final关键字的一些问题和比较)
- 黑马程序员-关于类的继承问题与final关键字的一些感悟
- java 关键字 final 的一些误区
- final关键字修饰变量的几点思考
- Java 中的 final 关键字的一些注意事项小记
- super、final、abstract关键字、以及面向抽象编程的一些注意点
- Java关键字final, static一些要点
- 关于大型系统下数据库的一些思考
- Spring-Boot获取部署项对jar中内容获取的一些思考
- Java--final关键字
- Java关键字final、static使用总结
- 关于关键词抽取的一些思考
- .Net开源的一些思考