Java内部类汇总

当一个类的定义出现在另外一个类的类体中,这个类叫做内部类,这个类所在的类叫做外部类

普通内部类:直接将一个类的定义放在另外一个类的类体中

静态内部类:使用static关键字修饰的内部类,隶属于类层级

局部内部类:直接将一个类的定义放在方法体的内部时。

匿名内部类:没有名字的内部类

普通内部类(成员内部类)

/**

 * 编程实现普通内部类的定义和使用  --文档注释

 */

public class NormalOuter {

    private int cnt = 1;

    //定义普通内部类  内部类也属于成员,和成员变量是平级的 并且是对象层级

    public class NormalInner {

        private int ia = 2;

        public NormalInner(){

            System.out.println("普通内部类的构造方法体执行到了");

        }

        public void show() {

            System.out.println("外部类中变量cnt的数值为:" + cnt);

            System.out.println("内部类的成员变量ia的数值为:" + ia);

        }

    }

}

public class NormalOuterTest {

    public static void main(String[] args) {

        //1.声明NormalOuter类型的引用指向该类型的对象

        NormalOuter nt1 = new NormalOuter();

        //声明NormalOuter类中内部类的引用指向内部类的对象

        NormalOuter.NormalInner ni = nt1.new NormalInner();

        //调用内部类中的show方法

        ni.show();

    }

}

普通内部类的构造方法体执行到了

外部类中变量cnt的数值为:1

内部类的成员变量ia的数值为:2

普通内部类需要使用外部类对象来创建对象

如果内部类访问外部类中与本类内部同名的成员变量或方法时,需要使用this关键字

例:

public class NormalOuter {

    private int cnt = 1;

    //定义普通内部类  内部类也属于成员,和成员变量是平级的 并且是对象层级

    public class NormalInner {

        private int ia = 2;

        private int cnt = 3;

        public NormalInner(){

            System.out.println("普通内部类的构造方法体执行到了");

        }

        public void show() {

            System.out.println("外部类中变量cnt的数值为:" + cnt);  //局部优先原则

            System.out.println("内部类的成员变量ia的数值为:" + ia);

        }

        public void show2(int cnt) {

            System.out.println("形参变量cnt = " + cnt);  //局部优先原则

            System.out.println("内部类中cnt = " + this.cnt);

            System.out.println("外部类中cnt = " + NormalOuter.this.cnt);

        }

    }

}

public class NormalOuterTest {

    public static void main(String[] args) {

        //1.声明NormalOuter类型的引用指向该类型的对象

        NormalOuter nt1 = new NormalOuter();

        //声明NormalOuter类中内部类的引用指向内部类的对象

        NormalOuter.NormalInner ni = nt1.new NormalInner();

        //调用内部类中的show方法

        ni.show();

        System.out.println("=====================================");

        ni.show2(4);

    }

}

普通内部类的构造方法体执行到了

外部类中变量cnt的数值为:3

内部类的成员变量ia的数值为:2

=====================================

形参变量cnt = 4

内部类中cnt = 3

外部类中cnt = 1


静态内部类

public class StaticOuter {

    private int cnt = 1;        //隶属于对象层级

    private static int snt = 2;         //隶属于类层级

    /**

     * 定义静态内部类

     */

    public static class StaticInner{

        private int ia = 3;

        public StaticInner() {

            System.out.println("静态内部类的构造方法哦");

        }

        public void show() {

            System.out.println("ia = " + ia);

            System.out.println("外部类中的snt = " + snt);

            //System.out.println("外部类中的cnt = " + cnt); //静态上下文中不能访问非静态的成员

        }

    }

}

public class StaticOuterTest {

    public static void main(String [] args) {

        //1.声明StaticInner类型的引用指向该类型对象

        StaticOuter.StaticInner st = new StaticOuter.StaticInner(); //静态类属于类层级

        //2.调用show方法进行测试

        st.show();

    }

}

静态内部类的构造方法哦

ia = 3

外部类中的snt = 2

静态内部类的使用:

public class StaticOuter {

    private int cnt = 1;        //隶属于对象层级

    private static int snt = 2;         //隶属于类层级

    public void show() {

        System.out.println("调用外部的show方法");

    }

    /**

     * 定义静态内部类

     */

    public static class StaticInner{

        private int ia = 3;

        private static int snt = 4;

        public StaticInner() {

            System.out.println("静态内部类的构造方法哦");

        }

        public void show() {

            System.out.println("ia = " + ia);

            System.out.println("外部类中的snt = " + snt);

        }

        public void show2(int snt) {

            System.out.println("snt = " + snt);

            System.out.println("内部类中的snt = " + StaticInner.snt);

            System.out.println("外部类中的snt = " + StaticOuter.snt);

            new StaticOuter().show(); //创建一个类变量,提升到类层级就可以访问外部类中的非静态方法

        }

    }

}

public class StaticOuterTest {

    public static void main(String [] args) {

        //1.声明StaticInner类型的引用指向该类型对象

        StaticOuter.StaticInner st = new StaticOuter.StaticInner(); //静态类属于类层级

        //2.调用show方法进行测试

        st.show();

        System.out.println("=====================================");

        st.show2(5);

    }

}

=====================================

snt = 5

内部类中的snt = 4

外部类中的snt = 2

调用外部的show方法

静态内部类不能访问外部类的非静态成员

静态内部类可以直接创建对象

没有static就是对象层级,有static就是类层级

局部(方法)内部类的格式

/**

 * 编程实现局部内部类的定义和使用

 */

public class AreaOuter {

    private int cnt = 1;

    public void show(){

        //定义一个局部变量进行测试, 从java8开始默认final关键字修饰

       final int ic = 4;

        //定义局部内部类,只在当前方法体的内部好用

        class AreaInner {

            private int ia = 2;

            public AreaInner(){

                System.out.println("局部内部类的构造方法");

            }

            public void test() {

                System.out.println("ia = " + ia);

                System.out.println("cnt = " + cnt);

                //ic = 5; Error需在定义时添加final,且不能改变

                System.out.println("ic= " + ic);

            }

        }

        //声明局部内部类的引用指向局部内部类的对象

        AreaInner ai = new AreaInner();

        ai.test();

    }

}

public class AreaOuterTest {

    public static void main(String[] args) {

        //1.声明外部类类型的引用指向外部类的对象

        AreaOuter ao = new AreaOuter();

        //2.通过show方法的调用实现局部内部内容类的定义和使用

        ao.show();

    }

}

局部内部类的构造方法

ia = 2

cnt = 1

ic= 4

局部内部类特点:

该方法的内部使用

局部内部类可以在方法体内部直接创建对象

局部内部类不能使用访问控制符(public private)和static关键字,方法内部的变量为局部变量,局部变量不能使用访问控制符,成员变量可以

局部内部类可以使用外部方法的局部变量,但是必须是final的。由局部内部类和局部变量的声明周期不同所致。

回调模式

如果一个方法的参数是接口类型,则在调用该方法时,需要创建并传递一个实现此接口类型的对象;而该方法在运行时会调用到参数对象中所实现的方法(接口中定义的)。

public interface AnonymousInterface {

    //1.自定义抽象方法

    public abstract void show();

}

public class AnonymousInterfaceImpl implements AnonymousInterface {

    @Override

    public void show() {

        System.out.println("这里是接口的实现类!");

    }

}

public class AnonymousInterfaceTest {

    //假设已有下面的方法

    //AnonymousInterface ai = new AnoymousInterfaceImpl();

    //接口类型的引用指向实现类型的对象,形成了多态

    public static void test(AnonymousInterface ai){

        ai.show();

    }

    public static void main(String[] args){

        //形参是一个接口类型的引用,不能直接new接口类型

        AnonymousInterfaceTest.test(new AnonymousInterfaceImpl());

    }

}

这里是接口的实现类!

经验:

当接口/类类型的引用作为方法的形参时,实参的传递方式有两种:

  1. 自定义类实现接口/继承类并重写方法,然后创建该类对象作为实参传递;
  2. 使用上述匿名内部类的语法格式得到接口/类类型的引用即可

匿名内部类的语法格式

pulss AnonymousInterfaceTest{

    //假设已有下面的方法

    //AnonymousInterface ai = new AnoymousInterfaceImpl();

    //接口类型的引用指向实现类型的对象,形成了多态

    public static void test(AnonymousInterface ai){

        ai.show();

    }

    public static void main(String[] args) {

        //形参是一个接口类型的引用,不能直接new接口类型

        //AnonymousInterfaceTest.test(new AnonymousInterfaceImpl());

        System.out.println("==============================");

        //使用匿名内部类的语法格式来得到接口类型的引用

        AnonymousInterface ait = new AnonymousInterface() {

            @Override

            public void show() {

                System.out.println("匿名内部类就是这么玩儿的,虽然你很抽象");

            }

        };

        //从java8开始提出新特性:lambda表达式:(参数列表) -> {方法体}

        //AnonymousInterface ait2 = () -> System.out.println("lambda表达式原来如此简单");;

        AnonymousInterfaceTest.test(ait);

    }

}

匿名内部类就是这么玩儿的,虽然你很抽象

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值