为什么内部类调用的外部变量必须是final修饰的?

因为生命周期的原因。方法中的局部变量,方法结束后这个变量就要释放掉,final保证这个变量始终指向一个对象。首先,内部类和外部类其实是处于同一个级别,内部类不会因为定义在方法中就会随着方法的执行完毕而跟随者被销毁。问题就来了,如果外部类的方法中的变量不定义final,那么当外部类方法执行完毕的时候,这个局部变量肯定也就被GC了,然而内部类的某个方法还没有执行完,这个时候他所引用的外部变量已经找不到了。如果定义为final,java会将这个变量复制一份作为成员变量内置于内部类中,这样的话,由于final所修饰的值始终无法改变,所以这个变量所指向的内存区域就不会变。 为了解决:局部变量的生命周期与局部内部类的对象的生命周期的不一致性问题

编程时,在线程中使用局部变量时候经常编译器会提示:局部变量必须声明为final

package test;

public class ThreadTest {
	
	public void function(String a) {
		
		new Thread(){
			@Override
			public void run() {
				System.out.println(a);
			}
		}.start();
	}
	
	
	public static void main(String[] args) {
		new ThreadTest().function("a");
		
	}
}

上图中由于方法function中的形参a没有声明为final,编译抛出异常:Cannot refer to the non-final local variable a defined in an enclosing scope

其实原因就是一个规则:java内部类访问局部变量时局部变量必须声明为final

public class ThreadTest {
	
	public void function(String a) {
		a="b";
		new Thread(){
			@Override
			public void run() {
				System.out.println(a);
			}
		}.start();
	}
	
	
	public static void main(String[] args) {
		new ThreadTest().function("a");
		
	}
}
在a="b"这一行报错: Local variable a defined in an enclosing scope must be final or effectively final

也就是说规则没有改变,只是java1.8的编译变得更加智能了而已,在局部变量没有重新赋值的情况下,它默认局部变量为final型,认为你只是忘记加final声明了而已。如果你重新给局部变量改变了值或引用,那就无法默认为final了,所以报错


  • 12
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值