final修饰的变量引用不能变还是对象不可变

Posted zzuli

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了final修饰的变量引用不能变还是对象不可变相关的知识,希望对你有一定的参考价值。

两种情况:如果是基本数据类型,被final修饰的变量一旦初始化就不能改变;如果是引用数据类型的变量,初始化之后不能只想另外一个对象。

基本数据类型:

package cn.yqg.day2;

public class StringTest {
     public static void main(String[] args) {
        final int a;
        int b=234;
        a=b;
        System.out.println(a);
    }
}

我们看到上面的代码a是final类型的,但是没有被初始化,所以可以给a赋值。如果a被初始化,a存储的值就不能改变了,示例如下。

package cn.yqg.day2;

public class StringTest {
     public static void main(String[] args) {
        final int a=123;
        int b=234;
        a=b;//编译通不过,会报错建议去掉fianl
        
        System.out.println(a);
    }
}

如果是引用数据类型

-----------------------------------------------------------------------------------------------------------------------------------------------------------------

package cn.yqg.day2;

public class StringTest {
     public static void main(String[] args) {
        final StringBuffer a=new StringBuffer("ppp");
        System.out.println(a);
        System.out.println(a.hashCode());
        a.append("kkk");
        System.out.println(a);
        System.out.println(a.hashCode());
        
    }
}

运行结果:

ppp
2018699554
pppkkk
2018699554

我们发现变量内容变了,引用没变。

我们把String定义为final类型,那么String类不能被继承,引用不能被改变,但是引用地址指向的内存的地址存储的对象是可以改变的

String a="ppp";
 a=a+"kkk";

我们看到a的对象内容改变了

不允许String类的引用被改变是为了安全性着想,我们看这个例子。

package cn.yqg.day3;

public class Test2 {
    public static void main(String[] args) {
        String a=new String("fds");
        String b=new String("ddd");
        String c=b;
        c=c+"ds";
        System.out.println(b);
        System.out.println(c);
    }
}

运行内存图:

技术分享图片
运行结果:

ddd
dddds

我们从此可以知道,上面的String c=b;并不是将b的地址复制给c,而是c新开辟一个地址并进行存贮,这就保证了String类的安全性,相反StringBuilder就存在安全隐患

package cn.yqg.day3;

public class Test2 {
    public static void main(String[] args) {
        StringBuilder s=new StringBuilder("ppp");
        StringBuilder r=s;
        r.append("kkk");
        System.out.println(r);
        System.out.println(s);
    }
}

运行结果:

pppkkk
pppkkk

r改变会导致s也改变,因为他们指向得内存地址一样。

------------------------------------------------------------------------------------------------------------------------------------------------------

 




以上是关于final修饰的变量引用不能变还是对象不可变的主要内容,如果未能解决你的问题,请参考以下文章

final关键字

final关键字!

用final修饰类,方法和变量的区别

final修饰的变量是引用不能改变,还是引用的对象不能改变???

java基础面试

从菜鸟程序员到高级架构师,竟然是因为这个字final