专栏原创出处:github-源笔记文件 (opens new window)github-源码 (opens new window),欢迎 Star,转载请附上原文出处链接和本声明。

Java 核心知识专栏系列笔记,系统性学习可访问个人复盘笔记-技术博客 Java 核心知识 (opens new window)

# 一、内部类是什么

把类定义在另一个类的内部,该类就被称为「内部类」。

内部类又根据定义的位置、类的修饰词不同分为:

  • 成员内部类
  • 静态内部类
  • 局部内部类
  • 匿名内部类

# 二、内部类种类

术语说明:

  • 成员 = 变量 + 方法
  • 静态成员 = 静态变量 + 静态方法
  • 非静态成员 = 非静态变量 + 非静态方法

# 1. 成员内部类

定义:位于外部类成员位置的类

大白话的理解:像定义类的非静态成员那样定义了一个类

public class MemberOuter {

    class MemberInner {}

    public static void main(String[] ages) {
        final MemberOuter memberOuter = new MemberOuter();
        final MemberOuter.MemberInner oi = memberOuter.new MemberInner();
    }
}

特点:

  • 可以访问外部类的「所有成员」,包括 private 修饰的
  • 创建对象范式,外部类对象实例.new 内部类 ()

# 2. 静态内部类

定义:位于外部类成员位置而且用 static 修饰的类

大白话的理解:像定义类的静态成员那样定义了一个类

public class StaticOuter {

    static class StaticInner {}

    public static void main(String[] ages) {
        final StaticOuter.StaticInner oi = new StaticOuter.StaticInner();
    }
}

特点:

  • 可以访问外部类的「所有静态成员」,包括 private 修饰的
  • 创建对象范式,new 外部类.内部类 ()

# 3. 局部内部类

定义:定义在一个方法或者一个作用域里面的类

大白话的理解:像变量一样声明一个类,只能在声明的作用域里使用

public class LocalOuter {
    {
        class LocalInner {}
        final LocalInner oi = new LocalInner();
    }

    public void showName() {
        class LocalInner {}
        final LocalInner oi = new LocalInner();
    }
}

特点:

  • 可以访问外部类的「所有成员」,包括 private 修饰的
  • 创建对象范式,在对应作用域中 new 内部类 ()

# 4. 匿名内部类

定义:没有名字的类

大白话的理解:没有起名字的类

new Thread(){
    @Override
    public void run() {
        super.run();
    }
};

特点:

  • 可以访问外部类的「所有成员」,包括 private 修饰的
  • 创建对象范式,在对应作用域中 new 类 (){}

# 三、应用场景

1. 私有性封装

外部类只能被 public/默认 2 个词修饰,如果想私有(private)只能设计为成员内部类。

如果某个类只想在某个方法里面使用,可以使用局部内部类。

比如: Iterator 接口的大多数实现类。

2. 组合

一个抽象类 S 实现一些模板方法,其他功能类可以组合若干个内部类(抽象类 S 的实现类)提供功能,对外来说,内部实现细节被屏蔽了。

比如: 锁与 AQS 的关系。

3. 减少类定义

对于需要继承或者实现的类,我们可以直接使用匿名内部类,不需要在声明 class。

限于篇幅,部分内部类变量访问代码参考源码 inner_class (opens new window)

最后修改时间: 2/17/2020, 4:43:04 AM