疯狂java


您现在的位置: 疯狂软件 >> 新闻资讯 >> 正文

final用法总结


 

    第一 final修饰类

  Final修饰的类没有子类,因为它不能被继承,例如java.lang.String类。Final类的所有方法都是final方法。

  注意:final不能跟abstract关键字连用,因为重现的类或者方法必须被继承和覆盖才有意义。

  第二 final修饰方法

  Final方法可以被子类继承,但是不能被子类重写。有人说,父类的private方法是final方法,不过我不这么认为。因为,父类的private方法可以被子类继承,也能被子类覆盖。

  第三 final修饰属性

  Final属性属于常量,只能被初始化一次,之后不能改变。初始化的方式有两种:

  1在声明时初始化

  Java代码

  class Test{

  final int age = 1;

  }

  2在构造方法中初始化

  Java代码

  class Test{

  final int age;

  Father(){

  age = 1;

  }

  }

  如果final修饰的是个引用变量,如StringBuffer,可以通过调用对象的方法、设置属性等改变其值。但是引用变量本身不能变。示例如下:

  Java代码

  //测试类

  class Test{

  public final StringBuffer sb = new StringBuffer("这是第一个字符串");

  public String appendString(String str){

  return this.sb.append(str).toString();

  }

  }

  //演示类

  class Demo{

  public void mytest(){

  Test t = new Test();

  //错误,因为它对属性sb又一次赋值了

  t.sb = "赋值为新字符串";

  //正确,以为它并没有改变sb的引用地址

  t.sb.append("添加点东西");

  //正确,理由同上

  t.appendString("又添了一点东西");

  }

  }

  第四 final修饰局部变量

  Final局部变量,例如,在一个函数中声明的一个局部变量,JVM会在程序的栈内存中为该变量开辟空间。而堆内存是由GC(垃圾回收器)管理的,所以当函数结束时,该变量依然存在,可以被其他线程或程序段使用,不至于出现空指针异常。这个用法在多线程、定时器和内部类中较为常见。例如:

  Java代码

  import java.util.Timer;

  import java.util.TimerTask;

  public class FinalTest {

  public static void test(){

  final Timer timer = new Timer();

  final int count = 1;

  timer.schedule(new TimerTask(){

  @Override

  public void run(){

  System.out.println("2,test方法,输出count=="+count);

  //....

  //....

  //这一句使用了timer变量

  timer.cancel();

  }

  },1000,2000);

  }

  public static void main(String[] args) {

  FinalTest.test();

  System.out.println("1,这句话应该在test方法之后运行");

  }

  }

  运行结果是:

  1,这句话应该在test方法之后运行

  2,test方法,输出count==1

  第五 final修饰方法参数

  Final参数跟final属性差不多,都是不能更改其值。但是如果参数是引用变量的话可以设置其属性和调用其方法。