精华内容
下载资源
问答
  • Java匿名内部类访问外部类的局部变量,那么这个局部变量需要用final修饰吗? 为什么我的测试没有用final却可以?
  • 内部类的同名变量访问_解决方法: 格式:外部类名称.this.外部类成员变量名 如何创建内部类对象 格式:外部类名称.内部类名称 对象名 = new 外部类名称().new 内部类名称(); 实例如下: 定义一个包含内部类的...

    内部类的同名变量访问_解决方法:

    格式:外部类名称.this.外部类成员变量名

    如何创建内部类对象

    格式:外部类名称.内部类名称 对象名 = new 外部类名称().new 内部类名称();

    实例如下:

    定义一个包含内部类的外部类:

    package NeiBuLei;
    
    //如果出现了重名现象,那么格式是:外部类名称.this.外部类成员变量名
    
    public class Outer {
    
        int num = 10; // 外部类成员变量
    
        public class Inner{
    
            int num = 20; // 内部类成员变量
    
            public void methodInner(){
                int num = 30; // 内部类方法的局部变量
                System.out.println(num); // 局部变量,就近原则
                System.out.println(this.num); // 内部类的成员变量
                System.out.println(Outer.this.num); // 外部类的成员变量
            }
        }
    }
    

    使用这个类:

    package NeiBuLei;
    
    public class Demo01InnerClass {
        public static void main(String[] args) {
            //外部类名称.内部类名称 对象名 = new 外部类名称().new 内部类名称();
            Outer.Inner inner = new Outer().new Inner();
    
            inner.methodInner();
        }
    }
    

    运行结果:

    30
    20
    10

     

    展开全文
  • 那么,Java匿名内部类访问外部变量,为何需被标志为final?这跟上述三个特性有关系吗? 一、问题的提出 Java编程中,使用匿名内部类访问外部方法的局部变量是一件很常见的事件,比如以下代码,使用匿名内部...

    对于Java语言中的final使用,大家应该很熟悉,可以修饰类,表示不可继承;可以修饰方法,表示不可被子类重写;可以修饰变量,表示不可以被二次赋值。那么,Java匿名内部类访问外部变量,为何需被标志为final?这跟上述三个特性有关系吗?

    一、问题的提出

    Java编程中,使用匿名内部类访问外部方法的局部变量是一件很常见的事件,比如以下代码,使用匿名内部类设置控件的监听器是再常见不过了,下面的例子中,因为匿名监听器类访问了外部局部变量name,编译器提示name变量必须使用final修饰。

      //初始化按钮的监听器
        public void initListener(Button btn ){
            final int name = "王大锤"; //必须标记为final
    
            btn.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    btn.setText(name); //动态改变按钮的文字
                }
            });
        }

    为何name变量需被标志为final?这深层次的原因是什么?为什么有这样一个让人摸不着头脑的规定?

    二、解释

    • 这要从闭包说起,匿名内部类和外部方法形成了一个闭包,因此,匿名内部类能够访问外部方法的变量,看起来是一种“天经地义”的事情,Java语言当然也需要实现这种特性,但是这里遇到了一个问题。

    • 匿名内部类的生命周期可能比外部的类要长,因此访问外部局部变量有可能是访问不到的。

    • 那怎么办呢?Java语言为了实现这种特性, 只好将外部的局部变量偷偷的赋值了一份给匿名内部类。那这样匿名内部类就可以肆无忌惮的访问外部局部变量了。

    • 问题又来了,这种通过赋值的形式有一个缺陷,匿名内部类不可以修改“原来的局部变量”,因为是一份“复制品”,修改复制品对原变量没什么影响啊。

    • 那怎么办? Java语言干脆强制要求被匿名内部类访问的外部局部变量必须是final的,什么意思呢?就是“一刀切”,不让修改了。

    展开全文
  • 原文地址 ... ...对于Java语言中的final使用,大家应该很熟悉,可以修饰,表示不...那么,Java匿名内部类访问外部类的局部变量,为何需被标志为final?这跟上述三个特性有关系吗? 一、问题的提出 Java

    原文地址

    http://www.jianshu.com/p/609ca1c584ac

    对于Java语言中的final使用,大家应该很熟悉,可以修饰类,表示不可继承;可以修饰方法,表示不可被子类重写;可以修饰变量,表示不可以被二次赋值。那么,Java匿名内部类访问外部类的局部变量,为何需被标志为final?这跟上述三个特性有关系吗?

    一、问题的提出

    Java编程中,使用匿名内部类访问外部方法的局部变量是一件很常见的事件,比如以下代码,使用匿名内部类设置控件的监听器是再常见不过了,下面的例子中,因为匿名监听器类访问了外部局部变量name,编译器提示name变量必须使用final修饰。

      //初始化按钮的监听器
        public void initListener(Button btn ){
            final int name = "王大锤"; //必须标记为final
    
            btn.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    btn.setText(name); //动态改变按钮的文字
                }
            });
        }

    为何name变量需被标志为final?这深层次的原因是什么?为什么有这样一个让人摸不着头脑的规定?

    二、解释

    • 这要从闭包说起,匿名内部类和外部方法形成了一个闭包,因此,匿名内部类能够访问外部方法的变量,看起来是一种“天经地义”的事情,Java语言当然也需要实现这种特性,但是这里遇到了一个问题。

    • 匿名内部类的生命周期可能比外部的类要长,因此访问外部局部变量有可能是访问不到的。

    • 那怎么办呢?Java语言为了实现这种特性, 只好将外部的局部变量偷偷的赋值了一份给匿名内部类。那这样匿名内部类就可以肆无忌惮的访问外部局部变量了。

    • 问题又来了,这种通过赋值的形式有一个缺陷,匿名内部类不可以修改“原来的局部变量”,因为是一份“复制品”,修改复制品对原变量没什么影响啊。

    • 那怎么办? Java语言干脆强制要求被匿名内部类访问的外部局部变量必须是final的,什么意思呢?就是“一刀切”,不让修改了。

    概括,匿名内部类因为闭包可以访问外部类的变量,但是因为生命周期的原因,内部类可能会访问不到外部类的变量,所以将外部类的变量赋值了一份给匿名内部类,现在可以访问了,但是又因为无法修改外部类变量的内容,最后干脆让外部类的局部变量写成不可变的。
    展开全文
  • 文章目录1 内部类的基本概念1.1 内部类的定义1.2 内部类的优缺点2 创建内部类2.1 在外部类外部创建非静态内部类2.2 在外部类外部创建静态内部类2.3 在外部类内部创建内部类语法3 内部类的分类3.1 成员内部类3.2 静态...

    1. 内部类的基本概念

    1.1 内部类的定义

    内部类: 所谓内部类就是在一个类内部进行其他类结构的嵌套操作。

    class Outer{
        private String str ="外部类中的字符串";
        //************************** 
        //定义一个内部类
        class Inner{
            private String inStr= "内部类中的字符串";
            //定义一个普通方法
            public void print(){
                //调用外部类的str属性
                System.out.println(str);
            }
        }
        //************************** 
        //在外部类中定义一个方法,该方法负责产生内部类对象并调用print()方法
        public void fun(){
            //内部类对象
            Inner in = new Inner();
            //内部类对象提供的print
            in.print();
        }
    }
    public class Test{
        public static void main(String[] args)
        {
            //创建外部类对象
            Outer out = new Outer();
            //外部类方法
            out.fun();
        }
    }
    

    运行结果:外部类中的字符串
    但是如果去掉内部类:

    class Outer{
        private String outStr ="Outer中的字符串";
        public String getOutStr()
        {
            return outStr;
        }
        public void fun(){  //2
            //this表示当前对象
            Inner in = new Inner(this); //3
            in.print();                 //5
        }
    }
    class Inner{
        private String inStr= "Inner中的字符串";
        private Outer out;
        //构造注入
        public Inner(Outer out)  //3
        {
            this.out=out;       //4.为Inner中的out变量初始化
        }
        public void print(){    //6
            System.out.println(out.getOutStr()); //7
        }
    } 
    public class Test{
        public static void main(String[] args)
        {
            Outer out = new Outer();  //1.
            out.fun(); //2.
        }
    }
    

    执行结果:Outer中的字符串
    但是去掉内部类之后发现程序更加难以理解。

    1.2 内部类的优缺点

    内部类的优点:

    1. 内部类与外部类可以方便的访问彼此的私有域(包括私有方法、私有属性)。
    2. 内部类是另外一种封装,对外部的其他类隐藏。
    3. 内部类可以实现java的单继承局限。

    内部类的缺点:

    结构复杂。
    记录:使用内部类实现多继承:

    class A {
        private String name = "A类的私有域";
        public String getName() {
            return name;
        }
    }
    class B {
        private int age = 20;
        public int getAge() {
            return age;
        }
    }
    class Outter {
        private class InnerClassA extends A {
            public String name() {
                return super.getName();
        }
    }
        private class InnerClassB extends B {
            public int age() {
                return super.getAge();
        }
    }
        public String name() {
            return new InnerClassA().name();
        }
        public int age() {
            return new InnerClassB().age();
        }
    }
    public class Test2 {
            public static void main(String[] args) {
                Outter outter = new Outter();
                System.out.println(outter.name());
                System.out.println(outter.age());
            }
    }
    

    在这里插入图片描述

    2. 创建内部类

    2.1 在外部类外部 创建非静态内部类

    语法: 外部类.内部类 内部类对象 = new 外部类().new 内部类();
    举例: Outer.Inner in = new Outer().new Inner();

    2.2 在外部类外部 创建静态内部类

    语法: 外部类.内部类 内部类对象 = new 外部类.内部类();
    举例: Outer.Inner in = new Outer.Inner();

    2.3 在外部类内部创建内部类语法

    在外部类内部创建内部类,就像普通对象一样直接创建:Inner in = new Inner();

    3. 内部类的分类

    在Java中内部类主要分为成员内部类、静态内部类、方法内部类、匿名内部类

    3.1 成员内部类

    类比成员方法

    1. 成员内部类内部不允许存在任何static变量或方法 正如成员方法中不能有任何静态属性 (成员方法与对象相关、静态属性与类有关)
    class Outer {
        private String name = "test";
        public  static int age =20;
    
        class Inner{
            public static int num =10;
            public void fun()
            {
                System.out.println(name);
                System.out.println(age);
            }
        }
    }
    public class Test{
        public static void main(String [] args)
        {}
    }
    

    在这里插入图片描述
    2. 成员内部类是依附外部类的,只有创建了外部类才能创建内部类。

    3.2 静态内部类

      关键字static可以修饰成员变量、方法、代码块、其实还可以修饰内部类,使用static修饰的内部类我们称之为静态内部类,静态内部类和非静态内部类之间存在一个最大的区别,非静态内部类在编译完成之后会隐含的保存着一个引用,该引用是指向创建它的外围类,但是静态类没有。没有这个引用就意味着:
      1.静态内部类的创建不需要依赖外部类可以直接创建。
      2.静态内部类不可以使用任何外部类的非static类(包括属性和方法),但可以存在自己的成员变量。

    class Outer {
        public String name = "test";
        private static int age =20;
    
        static class Inner{
            private String name;
            public void fun()
            {
                System.out.println(name);
                System.out.println(age);
            }
        }
    }
    public class Test{
        public static void main(String [] args)
        {
            Outer.Inner in = new Outer.Inner();
        }
    }
    

    在这里插入图片描述

    3.3 方法内部类

    方法内部类顾名思义就是定义在方法里的类
    1.方法内部类不允许使用访问权限修饰符(public、private、protected)均不允许。

    class Outer{
        private int num =5;
        public void dispaly(final int temp)
        {
            //方法内部类即嵌套在方法里面
            public class Inner{
            }
        }
    }
    public class Test{
        public static void main(String[] args)
        {}
    }
    

    在这里插入图片描述
    2. 方法内部类对外部完全隐藏,除了创建这个类的方法可以访问它以外,其他地方均不能访问 (换句话说其他方法或者类都不知道有这个类的存在)方法内部类对外部完全隐藏,出了创建这个类的方法可以访问它,其他地方均不能访问。
    3. 方法内部类如果想要使用方法形参,该形参必须使用final声明(JDK8形参变为隐式final声明)

    class Outer{
        private int num =5;
        //普通方法
        public void dispaly(int temp)
        {
            //方法内部类即嵌套在方法里面
            class Inner{
                public void fun()
                {
                    System.out.println(num);
                    temp++;
                    System.out.println(temp);
                }
            }
            //方法内部类在方法里面创建
            new Inner().fun();
        }
    }
    public class Test{
        public static void main(String[] args)
        {
            Outer out = new Outer();
            out.dispaly(2);
        }
    }
    

    在这里插入图片描述

    3.4 匿名内部类

      匿名内部类就是一个没有名字的方法内部类,因此特点和方法与方法内部类完全一致,除此之外,还有自己的特点:
    1.匿名内部类必须继承一个抽象类或者实现一个接口。
    2.匿名内部类没有类名,因此没有构造方法。

    //匿名内部类
    //声明一个接口
    interface MyInterface {
        //接口中方法没有方法体
        void test();
    }
    class Outer{
        private int num = 5;
        public void dispaly(int temp)
        {
            //匿名内部类,匿名的实现了MyInterface接口
            //隐藏的class声明
            new MyInterface()
            {
                public void test()
                {
                    System.out.println("匿名实现MyInterface接口");
                    System.out.println(temp);
                }
            }.test();
        }
    }
    public class Test{
        public static void main(String[] args)
        {
            Outer out = new Outer();
            out.dispaly(3);
        }
    }
    

    在这里插入图片描述

    4. 内部类与外部类的关系

    • 对于非静态的内部类,内部类的创建依赖外部类的实例对象,在没有外部类实例之前是无法创建内部类的。
    • 内部类可以直接访问外部类的元素(包括私有域)—外部类在内部类之前创建,创建内部类时会将外部类的对象传入
    class Outer{
        //成员变量  与对象有关
        private String msg;
        private int age;
        //--------------------------
        class Inner{
            public void dispaly()
            {
                //此处有一个隐藏的Outer.this
                msg = "test";
                age = 20;
                System.out.println(msg);
                System.out.println(age);
            }
        }
        //--------------------------
        public void test()
        {
            Inner in = new Inner();
            in.dispaly();
        }
    }
    public class Test{
        public static void main(String[] args)
        {
            Outer out = new Outer();
            out.test();
        }
    }
    
    • 外部类可以通过内部类的引用间接访问内部类元素 – -要想访问内部类属性,必须先创建内部类对象
    class Outer{
        public void dispaly()
        {
            //外部类通过创建内部类的对象间接访问内部类元素
            Inner in = new Inner();
            in.dispaly();
        }
        class Inner{
            public void dispaly()
            {
                System.out.println("内部类");
            }
        }
    }
    public class Test1{
        public static void main(String[] args)
        {
            Outer out = new Outer();
            out.dispaly();
        }
    }
    
    • 内部类是一个相对独立的个体,与外部类没有关系。
    展开全文
  • 匿名内部类不能访问外部类方法中的局部变量,除非变量被声明为final类型 这里所说的“匿名内部类”主要是指在其外部的成员方法内定义,同时完成实例化的,若其访问该成员方法中的局部变量,局部变量必须要被...
  • java内部类面试题: java内部类分类: 成员内部,局部内部,静态内部,匿名内部 静态内部不能访问外部类的属性方法,所以android开发过程中可以优化handler 其他内部可以访问外部类,是因为持有外部...
  • JAVA中non-static内部类能够访问外部类的实例成员和静态成员,而static内部类只能访问外部类的实例成员。 匿名内部类访问外部外部方法中的局部变量时,此局部变量必须为final类型 public void testThread(){ ...
  • 今天看到Java语法书内部类中的 匿名nei
  • java 匿名类访问外部变量要使用final

    千次阅读 2016-02-26 13:51:02
    1) 从程序设计语言的理论上:局部内部类(即:定义在方法中的内部类),由于本身就是在方法内部(可出现在形式参数定义处或者...3) JAVA语言的编译程序的设计者当然全实现:局部内部类访问方法中的所有的局部变量(因为:从理
  • Java 内部类外部类的关系

    千次阅读 2016-11-23 21:39:06
     内部类可以直接访问外部类的私有属性,这是由于这个原因。  1、非静态内部类对象会持有外部的对象。其实是,非静态内部类对象依赖于外部对象而存在,没有外部就没有内部类,有外部不一定有内部类。这一点...
  • Java内部类外部类互相访问问题

    千次阅读 2016-06-28 17:32:56
    今天在分析android的AMS的时候,发现在AMS中出现了内部类访问外部类私有方法的操作,一时之间觉得有些奇怪:为毛private的方法可以被访问??之前的认识是private方法是不可以通过对象方式调用的,但是现在的代码...
  • 因为内部类外部类的局部变量生命周期不一样,外部类方法执行完该局部变量可能会被释放掉,但该方法中的内部类可能还在执行(如线程),还要使用该变量,所以外部类变量设置为final的,变成常量,使用的时候内部类...
  • Java外部类可以访问内部类private变量

    千次阅读 2019-04-04 15:05:05
    在讲Singleton时我举例时用过这样一段代码:   ...public class SingletonDemo { ...相信你一定发现了一个问题:外部类中的getInstance()方法调用了内部类SingletonHolder中的private变量instance。
  • 写一个用来判断是否静态和非静态的能不能访问外部的静态变量和非静态变量,答案是静态内部类可以访问静态变量,而不可以访问的非静态内部类。 原因是:当一个静态内部类被使用的时候,它的外部一定已经...
  • 根据查找资料:百度:内部类访问外部变量; 如果内部类调用了外部中的变量,那么该变量必须申明为final类型,后来想到应该是生命周期的原因,因为方法内定义的变量是局部变量,离开该方法,变量就失去了作用,...
  • 关于内部类的问题: 局部内部类访问外部类的局部变量问题 编程时,在线程中使用局部变量时候经常编译器会提示:局部变量必须声明为final [java] view plain copy package test; public class ThreadTest { ...
  • ``` package 线程优先级; import java.awt.*;...如果不用静态变量的话我又不知道怎么在Runnable的匿名内部类访问外部循环的i,有没有什么办法在匿名内部类中能够访问外部的参数,而且不是常量不是静态变量
  • (1)内部类里面使用外部的局部变量时,其实就是内部类的对象在使用它,内部类对象生命周期中都可能调用它, 而内部类试图访问外部方法中的局部变量时,外部方法的局部变量很可能已经不存在了,那么就得延续其生命...
  • 如果Java允许匿名内部类访问非final的局部变量的话,那我们就可以在TryUsingAnonymousClass$1中修改paramInteger,但是这不会对number的值有影响,因为它们是不同的reference。 这就会造成数据不同步的问题。 ...
  • 众所周知,在定义成员方法或者成员变量的时候,可以给其加上一些...也就是说,在成员内部类中可以随意引用外部类的成员方法以及成员变量,即使这些成员方法或者成员变量被修饰了private.如在成员外部类中定义了一个i
  • 昨天下午字节跳动的面试中,问到了这个问题:内部类访问外部类的成员吗? 当时只是回答了静态内部类访问外部类的静态方法,成员内部类访问外部类的所有方法。然后面试官问我原因我就答不上来了。还是原来看的...
  • 从学习java的时候知道匿名内部类访问外部类变量,那为何呢。先从一个最简答的例子开始: public class InnerTest { private int num = 0; public static void main(String[] args) { InnerTest innerTest...
  • 内部类里,想引用外部类的对象,为什么是外部类.this而不是外部类加引用变量,还有.操作应该是成员操作符吧,这样this不就成了外部类成员了
  • 1,Java中的匿名内部类是如何实现的? 先定义一个接口: 1 2 3 public interface MyInterface { void doSomething(); } 然后创建这个接口的匿名子类: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 ...
  • 内部类要访问局部变量,局部变量必须定义成final类型     java中规定,内部类只能访问外部类中的成员变量,不能访问方法中定义的变量,如果要访问方法中的变量,就要把方法中的变量声明为...
  • 深入理解Java中为什么内部类可以访问外部类的成员

    万次阅读 多人点赞 2014-02-26 22:54:26
    内部类简介 虽然Java是一门相对比较简单的...其中一个疑惑就是为什么内部类对象可以访问外部类对象中的成员(包括成员变量和成员方法)? 早就想对内部类这个特性一探究竟了,今天终于抽出时间把它研究了一下。 内
  • 内部类访问外部类变量的问题

    万次阅读 2012-07-20 16:55:46
    ----------------------android培训、java培训、期待与您交流! ---------------------- package test; public class TestFinal { //只有定义成 final User user 才不会报错为什么? public void test( User ...
  • 内部类就相当于一个外部的成员变量,所以可以直接访问外部变量,外部不能直接访问内部类变量,必须通过创建内部类实例的方法访问。你想不通的肯定是指内部类的私有变量怎么可以被外部访问吧,按常规,私有变量...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 152,740
精华内容 61,096
关键字:

java内部类访问外部类变量

java 订阅