浅析java一些修饰符

一.final修饰符:
作用域:类、方法、成员变量、局部变量、入参等

  1. final修饰类:
    final修饰的类就是传说中的不可变类,比如jdk里的Integer,Double,String等常用的基本数据类型。同时这个类是不能被继承的,而它的成员变量可以根据需要设置为final,所有成员方法都默认为final,不能被重写。也就是说如果一个类你确定不想让其他类来继承的话可以选择final修饰。
  2. final修饰方法:
    final方法是不能被重写的,也就是说你确定这个方法不想被子类 覆盖的情况下才需要将其设置为final方法。
  3. final修饰成员变量:

    1. final修饰的成员变量,一旦被赋值以后就不能重新复制,包含两个层面:如果是基本数据类型的变量其数值在初始化之后就不能更改;如果是引用类型的变量,它在初始化之后就不能修改它的指向,就是不能再指向另外一个对象。
    2. final修饰的成员变量需要立即初始化。也就是说final修饰的成员变量需要在定义的时候就直接赋值,或者在构造器中对它进行赋值,也可以在代码块中对其赋值,因为编译后代码块中的代码是排在构造器中代码之前执行的,但是三者只能选择其一为变量赋值。
      private final String string = "hello world";//直接初始化
      public Test(String string) {
      this.string = string;//构造器初始化
      }
      {
      string="hello world";//代码块中初始化
      }

      当然如果将final字段设置为static,则它只能在定义时以及静态代码块中进行初始化。
  4. final修饰局部变量:
    因为系统不会为局部变量进行初始化,所以在定义final的局部变量时可以不对其进行初始化,与普通局部变量一样需要在使用之前进行初始化,但是final的局部变量只能赋值一次。
    final变量和普通变量的区别还在于当final变量是基本数据类型或者String时,如果能在编译期间明确知道它的具体值,则编译器会对它进行优化,直接将它作为常量来替换掉final变量。比如下面的代码:

@org.junit.Test
    public void testFinal(){
        String a="hello world";
        final String b="hello" ;
        String c = "hello";
        System.out.println(b==c);

        String d = b+" world";
        String e = c + " world";
        System.out.println(a==d);
        System.out.println(a==e);

        String f = "hello" + " world";
        System.out.println(a==f);
    }

输出结果:

true
true
false
true

从结果可以看出来d=b+” world” 相当于是”hello”+” world” 的结果,也就是说编译器在编译阶段将final b直接用”hello” 替换了。当然这种优化是在编译器在编译期间明确知道变量的值的前提下来进行优化的。
5. final修饰入参:
final修饰的入参的理解也许不是那么深入,首先看一段代码:

@org.junit.Test
    public void testFinalRucan(){
        int a = 10;
        StringBuilder string = new StringBuilder("hello");
        List<String> list = new ArrayList<String>();
        list.add(string.toString());
        xiuGaiRuCan(a,string,list);

        System.out.println(a);
        System.out.println(string);
        System.out.println(list);
    }

    public void xiuGaiRuCan(final int i, final StringBuilder string, final List<String> list){
//        i++;
//        string = new StringBuilder();
//        list = new ArrayList<String>();
        string.append(" world");
        list.add(string.toString());
    }

输出为:
0
hello world
[hello, hello world]

从代码中可以看出,final修饰的入参是不支持修改的,也就是说是不支持重新赋值的,就是代码中注释掉的部分,编译器就会直接报错的。但是final的入参是引用类型时,其对象的中的数据是可以修改的,只是不允许该引用指向其他对象。
一般final的入参可以用于在装载集合的函数中,我们把需要装载的集合定义为final,就可以保证在函数的执行过程中传入的集合引用不会被篡改。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值