A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© 黄树人 中级黑马   /  2012-9-21 22:12  /  1723 人查看  /  4 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

本帖最后由 黄树人 于 2012-9-22 11:00 编辑

使用final关键字修饰一个变量时,到底是指引用变量不能变,还是引用变量所指向的对象中的内容不能改变。
例如,对于如下语句:
final StringBuffer a=new StringBuffer("immutable");
执行如下语句将报告编译期错误:

     a=new StringBuffer("");
但是,执行如下语句则可以通过编译:

a.append(" broken!");
这是为什么呢?
还有在定义方法的参数时,可不可用采用如下形式来阻止方法内部修改传进来的参数对象:
public void method(final  StringBuffer  param)

{

}

求高手解释下这里面的原理


4 个回复

倒序浏览

final StringBuffer a=new StringBuffer("immutable");
执行如下语句将报告编译期错误:

     a=new StringBuffer("");
但是,执行如下语句则可以通过编译:

a.append(" broken!"); 毫无疑问,引用所指向的地址不能变。
而对象的内容可以变。
public void method(final  StringBuffer  param)

{

}

第二个问题是不可以的
param 被final 修饰  虽然他指向的对象不能变  但是对象自身的内容可以变的
回复 使用道具 举报
final StringBuffer a=new StringBuffer("immutable");  这句话意思是说你创建的这个字符串缓冲区不能变啦 就是a的指向不能变啦
a=new StringBuffer("");   这句话的意思是你创建了一个新的字符串缓冲区,并把它赋值给a  你意思就是让a重新指向,但是上句a已经不能改变了所以会报错
a.append(" broken!");    这句话的意思就是给你的创建的字符串缓冲区添加东西还是可以的
final是他的指向不能再改变了


  
回复 使用道具 举报
本帖最后由 陈振兴 于 2012-9-22 01:30 编辑

当利用final修饰一个属性(变量)的时候,此时的属性成为常量.
常量的地址不可改变,但在地址中保存的值(即对象的属性)是可以改变的。正如你的疑问一样,
final StringBuffer a=new StringBuffer("immutable");
执行如下语句将报告编译期错误:

    a=new StringBuffer("");//重新指向了一个引用,创建新的对象
但是,执行如下语句则可以通过编译:

a.append(" broken!"); 这就你是重新改变了SringBuffere的内容(视频中提到面盆原理),地址不会变的
而对象的内容可以变。
回复 使用道具 举报
final修饰引用类型的时候,只是保证了该引用不变,如果引用(即指针,地址)初始化了,那它就永远保持那个地址,那个地址指向的对象还是可以通过调用方法来改变它的状态。
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马