美文网首页
为什么匿名内部类和局部内部类只能访问final变量

为什么匿名内部类和局部内部类只能访问final变量

作者: Eric新之助 | 来源:发表于2016-12-02 15:35 被阅读386次

是变量的作用域的问题,因为匿名内部类是出现在一个方法的内部的,如果它要访问这个方法的参数或者方法中定义的变量,则这些参数和变量必须被修饰为final。

一个xx.java类里面有匿名内部类,编译出来的class文件会有xx.class 、xx$1.calss...
例如:

public class InnerClass {

 public static void test(final String s){            
     InnerClass c = new InnerClass(){ 
         public void m(){ 
             int x = s.hashCode();   
             System.out.println(x);  
         } 
    };  
 }
}

编译出来的两个class文件是:InnerClass.class和 InnerClass$1.class,代码分别如下:

package smartpush;

import java.io.PrintStream;

public class InnerClass
{
  public static void test(String s)
  {
    InnerClass c = new InnerClass(s) {
      public void m() {
        int x = this.val$s.hashCode();
      System.out.println(x);
  }
 };
}
}

package smartpush;

import java.io.PrintStream;

class 1 extends InnerClass
{
  public void m()
{
  int x = this.val$s.hashCode();
  System.out.println(x);
}
}

这说明虽然匿名内部类在方法的内部,但实际编译的时候,内部类会编译成一个inner_object,而外部类中的方法中的变量s只是方法的局部变量,s的作用域只在这个方法内部有效。查看反编译出来的源码,内部类 class 1

int x = this.val$s.hashCode();

内部类使用this.val$s引用了方法内部的变量s

对于一个final变量:
如果是基本数据类型的变量,则其数值一旦在初始化之后便不能更改;
如果是引用类型的变量,则在对其初始化之后便不能再让其指向另一个对象。

因此内部类要引用变量s,编译器就要保证s的引用 this.val$s在初始化后就不能再改变。
不然如果在内部类的方法执行前,s的引用指向了其他地方,例如
s="321"

这样匿名类的变量指向B而外部的变量却指向A了,这结果显然是不能接受的
于是为了保证变量引用的一致性,内部类只能访问final变量。

http://stackoverflow.com/questions/3910324/why-java-inner-classes-require-final-outer-instance-variables
http://stackoverflow.com/questions/1299837/cannot-refer-to-a-non-final-variable-inside-an-inner-class-defined-in-a-differen
http://feiyeguohai.iteye.com/blog/1500108
http://blog.csdn.net/woshichunchun/article/details/7925823
http://blog.csdn.net/axman/article/details/1460544

相关文章

  • 匿名内部类问题

    匿名内部类访问的外部类局部变量为什么要用final 修饰,jdk8为啥不需要了? 匿名内部类访问的外部类局部变量为...

  • Java内部类

    代码中包含成员内部类、内部类的同名变量访问、局部内部类、局部内部类final、匿名内部类

  • 匿名内部类中使用的局部变量设置为final

    匿名内部类不能访问外部类方法中的局部变量,除非变量被声明为final类型 1. 这里所说的“匿名内部类”主要是指在...

  • 内部类

    成员内部类 局部内部类(定义在方法内和定义在作用域内的类) 匿名内部类

  • 内部类引用外部类的局部变量要用final修饰

    为什么内部类引用外部类的局部变量时,此变量要用final修饰 如图 上面的代码是使用了匿名内部类的方式。Runna...

  • 匿名内部类的使用

    1.匿名内部类中局部变量的使用 在JDK8中,匿名内部类使用局部变量不再要求局部变量使用final修饰,那么是否我...

  • Java

    JDK8之前,匿名内部类访问局部变量,局部变量为什么必须要用 final 修饰。 我们先来看一段代码: 原因是:因...

  • java面向对象笔记

    面向对象三要素 抽象 接口 面向对象(局部内部类访问局部变量的问题) 匿名内部类

  • 内部类

    一 、内部类 内部类共分为四种:静态内部类,成员内部类,局部内部类,以及匿名内部类。 1、静态内部类:只能访问外部...

  • 为什么匿名内部类和局部内部类只能访问final变量

    是变量的作用域的问题,因为匿名内部类是出现在一个方法的内部的,如果它要访问这个方法的参数或者方法中定义的变量,则这...

网友评论

      本文标题:为什么匿名内部类和局部内部类只能访问final变量

      本文链接:https://www.haomeiwen.com/subject/mqxbkttx.html