【Java】山外有山,类外还有类

【Java】山外有山,类外还有类

内部类是Java语言中的一种特性,它允许在另一个类中定义一个类。

内部类可以是静态的(不依赖于外部类的实例),也可以是非静态的(依赖于外部类的实例)。

在本篇博客中,我们将首先介绍内部类的使用特点,而后介绍几种内部类:

静态成员内部类

非静态成员内部类

局部内部类

匿名内部类

首先来看看内部类的使用特点:

image-20240505175218453

内部类的使用特点

  1. 访问控制:内部类可以直接访问外部类的成员,包括私有成员。
  2. 封装性:内部类可以隐藏在外部类中,对外不可见,增加了封装性。
  3. 继承:内部类可以继承外部类的属性和方法,也可以继承其他类或实现接口。
  4. 多态:内部类可以实现外部类不能实现的接口,实现多态。
  5. 生命周期:内部类的生命周期与创建它的外部类对象的生命周期相关联。
  6. 作用域:内部类的作用域限定在外部类中,只能在外部类中被访问。

什么时候使用内部类

当一个事物内部,还有一个部分需要完整的结构去描述,而这个内部的完整结构又仅为外部事物提供服务,则整个内部的完整结构,最好使用内部类。

例如:人类都有心脏,人类本身需要用属性去描述,人类内部的心脏,也需要特殊的属性和行为去描述,则心脏可以被定义成内部类,人类中的一个心脏类。

在实际的开发场景中,可能会有以下情形:

  1. 实现回调:使用匿名内部类来实现一个回调接口。
  2. 创建辅助类:创建一些仅供外部类使用的辅助类。
  3. 实现多态:通过内部类实现多态,特别是在设计模式中,如适配器模式、观察者模式等。

格式例如:

public class Outer {
    class Inner {
        // ...
    }
}

静态成员内部类

格式:直接在定义内部类的时候加上static关键字

public class A{
    static class B{
        
    }
}

注意:

  1. 内部类可以定义属性,方法,构造等
  2. 静态内部类可以被final或者abstract修饰,被final修饰之后,不能被继承,被abstract修饰之后,不能new
  3. 静态内部类,不能调用外部类的非静态成员
  4. 内部类还可以被四种权限修饰符修饰

调用静态内部类成员:

外部类.内部类 对象名 = new 外部类.内部类()

使用示例:

public class OuterClass {
    public static int staticField = 10;

    static class StaticInnerClass {
        void display() {
            System.out.println(staticField);
        }
    }

    public static void main(String[] args) {
        StaticInnerClass inner = new StaticInnerClass();
        inner.display();
        //或者
        OuterClass.StaticInnerClass inner = new OuterClass.StaticInnerClass();
        inner.display();
    }
}

非静态成员内部类

格式:

public class A{
    class B{
        
    }
}

调用非静态内部类成员:

外部类.内部类 对象名 = new 外部类().new 内部类()

使用示例:

public class OuterClass {
    private String outerField = "外部类字段";

    class NonStaticInnerClass {
        void display() {
            System.out.println(outerField);
        }
    }

    public void createInner() {
        NonStaticInnerClass inner = new NonStaticInnerClass();
        inner.display();
    }
}

OuterClass outer = new OuterClass();
outer.createInner();
//或者
OuterClass.NonStaticInnerClass inner = new OuterClass().new NonStaticInnerClass();

局部内部类

局部内部类可以定义在方法中,代码块中,构造中。

例如:

  1. 辅助计算类
public class Calculator {
    public void calculate() {
        class Helper {
            int add(int a, int b) {
                return a + b;
            }
        }

        Helper helper = new Helper();
        int result = helper.add(5, 10);
        System.out.println("计算结果是: " + result);
    }
}
  1. 假如要完成临时任务
public class TaskRunner {
    public void runTask() {
        class Task {
            void execute() {
                System.out.println("执行临时任务");
            }
        }

        Task task = new Task();
        task.execute();
    }
}

内部类、接口、抽象类、普通类作方法参数

接口作为方法参数返回值,传递实参时,传递实现类对象。

接口作为返回值类型返回,实际返回的是实现类对象。

示例代码如下:

package com.hamburger.innerclass;

public class main {
    public static void main(String[] args) {
        Mouse mouse = new Mouse();
        method(mouse);
        USB usb = method01();
    }
    /*
        接口作为方法参数,传递实参时,传递实现类对象
     */
    public static void method(USB usb){
        usb.open();
    }

    public static USB method01(){
        Mouse mouse = new Mouse();
        return mouse;

    }
}
package com.hamburger.innerclass;

public interface USB {
    public abstract void open();
}
package com.hamburger.innerclass;

public class Mouse implements USB{
    public void open(){
        System.out.println("haha");
    }
}

抽象类

  1. 作为方法参数传递,传递实参时,传递的是其子类对象。
  2. 作为方法返回值类型返回,实际返回的是其子类对象。

普通类

  1. 作为方法参数传递,传递的是对象
  2. 作为方法返回值返回,返回的是对象

匿名内部类

匿名内部类,可以理解为没有显式声明出类名的内部类。它没有类名,通常用于创建一次性使用的类对象,特别是当需要快速实现某个接口或继承某个类时。

使用场景:我们如果想要实现接口,简单使用一次抽象方法,就需要:

创建一个实现类

实现这个接口

重写抽象方法

new实现类方法

如果我们只想单纯使用一次接口中的方法,能不能不要这么麻烦?

使用匿名内部类的方法:

  1. 创建实现类,实现接口
  2. 重写方法
  3. 创建实现类对象
  4. 调用方法

匿名内部类格式:

new 接口/抽象类(){
    重写方法
}.重写的方法();
===============================
类名 对象名 = new 接口/抽象类(){
    重写方法
}
对象名.重写的方法();

匿名内部类作为参数传递

package com.ham.niminginnerclass;
public class test {
    public static void main(String[] args){

        method(new USB() {
            @Override
            public void open() {
                System.out.println("lzy");
            }

            @Override
            public void close() {
                System.out.println("dyp");
            }
        }); 
    }
    public static void method(USB usb){
        usb.open();
        usb.close();
    }
}

package com.ham.niminginnerclass;

public interface USB {
    public abstract void open();
    public abstract void close();
}

匿名内部类的使用场景:

  1. 事件监听器:在需要为事件添加监听器时,可以利用匿名内部类快速实现接口中的方法。
  2. 线程的实现:创建线程时,可以匿名内部类实现Runnable接口。
  3. 临时任务:当需要临时实现某个接口,且该实现不需要复用时。
  4. 回调函数:在需要提供回调函数时,可以使用匿名内部类快速实现。
  5. 实现策略模式:在实现策略模式时,可以使用匿名内部类来定义不同的策略。

使用示例

  1. 当需要创建一个线程来执行特定的任务时,可以使用匿名内部类实现Runnable接口:
// 使用匿名内部类创建线程
new Thread(new Runnable() {
    @Override
    public void run() {
        System.out.println("线程运行中");
    }
}).start();
  1. 在对对象数组进行排序时,可能需要提供一个自定义的比较器,这时可以使用匿名内部类:
// 使用匿名内部类实现比较器
String[] strings = {"banana", "apple", "orange"};
Arrays.sort(strings, new Comparator<String>() {
    @Override
    public int compare(String o1, String o2) {
        return o1.compareTo(o2);
    }
});
  1. 当需要临时实现一个接口,并且这个实现不需要在其他地方复用时,可以使用匿名内部类:
// 使用匿名内部类实现临时任务
public void performTask() {
    Task task = new Task() {
        @Override
        public void execute() {
            System.out.println("执行临时任务");
        }
    };
    task.execute();
}

结语

参考文档如下:

【Java】内部类的使用方法和使用特点-CSDN博客

Java内部类详解(含:成员内部类、局部内部类、匿名内部类、静态内部类)-CSDN博客

36.内部类介绍_哔哩哔哩_bilibili

本篇作为复习内部类时的一部分笔记与总结,在之后仍会对本文不够详细之处作修订与补充。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/594131.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

在R的 RGui中,使用devtools 安装trajeR

创建于&#xff1a;2024.5.5 文章目录 1. 报错信息2. 尝试使用指定的清华镜像&#xff0c;没有解决3. 找到原因&#xff1a;官网把包删除了4. 尝试从网上下载&#xff0c;然后安装。没有成功5. 使用devtools安装5.1 尝试直接安装&#xff1a;install.packages("devtools&q…

【智能算法应用】混合粒子群算法求解CVRP问题

目录 1.算法原理2.数学模型3.结果展示4.参考文献5.代码获取 1.算法原理 【智能算法】粒子群算法&#xff08;PSO&#xff09;原理及实现 经典PSO算法用于连续空间优化问题&#xff0c;VRP问题为离散组合优化问题&#xff0c;涉及如何有效地分配一组车辆去访问多个客户点&…

OSEK的设计哲学与架构

1 前言 OSEK是为单核分布式嵌入式控制单元量身定制的实时系统&#xff0c;对事件驱动&#xff08;event driven&#xff09;的硬实时控制系统具有良好的适配性。OSEK没有强求不同软件模块间的完全兼容性&#xff0c;而是将重心放到了软件的可移植性上来。简单来说&#xff0c;与…

[报错解决]Communications link failure

报错 主机IDEA项目连接虚拟机的数据库报错。 主要报错信息有&#xff1a; com.mysql.cj.jdbc.exceptions.CommunicationsException: Communications link failure The last packet sent successfully to the server was 0 milliseconds ago. The driver has not received a…

智慧旅游引领未来风尚,科技助力旅行更精彩:科技的力量推动旅游业创新发展,为旅行者带来更加便捷、高效和智能的旅行服务

目录 一、引言 二、智慧旅游的概念与特点 &#xff08;一&#xff09;智慧旅游的概念 &#xff08;二&#xff09;智慧旅游的特点 三、科技推动旅游业创新发展 &#xff08;一&#xff09;大数据技术的应用 &#xff08;二&#xff09;人工智能技术的应用 &#xff08;…

Linux Ubuntu 开机自启动浏览器

终端输入命令&#xff1a;gnome-session-properties 打开启动设置 如果提示&#xff1a;Command ‘gnome-session-properties’ not found, but can be installed with: apt install gnome-startup-applications 则执行&#xff1a;apt install gnome-startup-applications安装…

一、写给Android开发者之harmony入门

一、创建新项目 对比 android-studio&#xff1a;ability类似安卓activity ability分为两种类型(Stage模型) UIAbility和Extensionability&#xff08;提供系统服务和后台任务&#xff09; 启动模式 1、 singleton启动模式&#xff1a;单例 2、 multiton启动模式&#xff1…

数据结构十:哈希表

本次将从概念上理解什么是哈希表&#xff0c;理论知识较多&#xff0c;满满干货&#xff0c;这也是面试笔试的一个重点区域。 目录 一、什么是哈希表 1.0 为什么会有哈希表&#xff1f; 1.1 哈希表的基本概念 1.2 基本思想 1.3 举例理解 1.4 存在的问题 1.5 总结 二、…

libcity笔记:参数设置与参数优先级

1 参数优先级 高优先级的参数会覆盖低优先级的同名参数 Libcity中的优先级顺序维&#xff1a; 命令行参数&#xff08;命令行python run_model.py时导入的&#xff09; > 用户定义配置文件&#xff08;命令行python run_model.py时由config_file导入的&#xff09; >…

javascript 练习 写一个简单 另类录入 电脑组装报价表 可打印

数据格式 &#xff08;1代表cpu、2代表主板、3代表内存、。。。&#xff09; 1i3 12100 630 2H610 480 3DDR4 3200 16G 220 4500G M.2 299 5300W电源 150 6小机箱 85 7GT 730G 4G 350 8WD 2T 399 9飞利浦 24Led 580 主代码 Html JS <!DOCTYPE html> <html lang&qu…

02_Java综述

目录 面向对象编程两种范式抽象OOP 三原则封装继承多态多态、封装与继承协同工作 面向对象编程 面向对象编程(Object-Oriented Programming&#xff0c;OOP)在Java中核心地位。几乎所有的Java程序至少在某种程度上都是面向对象的。OOP与java是密不可分的。下面说一下OOP的理论…

SSM+Vue酒店管理系统

SSMVue酒店管理系统&#xff0c;JavaWeb酒店管理系统&#xff0c;项目由maven工具管理依赖&#xff0c;数据库Mysql&#xff0c;一共19张表&#xff0c;前端用Vue写的管理端&#xff0c;功能丰富&#xff0c;需要可在最后位置联系我&#xff0c;可加购调试&#xff0c;讲解&…

自注意力架构大成者_Transformer(Pytorch 17)

1 模型简介 在上节比较了 卷积神经网络&#xff08;CNN&#xff09;、循环神经网络&#xff08;RNN&#xff09;和 自注意力&#xff08;self‐attention&#xff09;。值得注意的是&#xff0c; 自注意力同时具有并行计算和最短的最大路径长度这两个优势。因此&#xff0c;使…

Llama3本地部署与高效微调入门

前言 为了保持公司在AI&#xff08;人工智能&#xff09;开源大模型领域的地位&#xff0c;社交巨头Meta推出了旗下最新开源模型。当地时间4月18日&#xff0c;Meta在官网上宣布公布了旗下最新大模型Llama 3。目前&#xff0c;Llama 3已经开放了80亿&#xff08;8B&#xff09…

8086 汇编学习 Part 9

端口的读写 CPU 的邻居 CPU 内部的寄存器内存单元端口&#xff08;各种接口卡、网卡&#xff0c;显卡&#xff0c;主板上的接口芯片等&#xff09; 各种芯片工作时&#xff0c;都有一些寄存器由 CPU 读写从 CPU 角度&#xff0c;将各寄存器当端口&#xff0c;并统一编制CPU …

开源im即时通讯app源码系统/php即时聊天im源码/php+uniapp框架【终身使用】

摘要 随着开源文化的蓬勃发展&#xff0c;即时通讯(IM)系统作为现代通信不可或缺的一部分&#xff0c;其开源实现正变得越来越普遍。本文将深入探讨基于PHP的全开源即时通讯源码系统&#xff0c;并结合UniApp开源框架&#xff0c;从理论基础到代码实现&#xff0c;再到实际应用…

探索设计模式的魅力:分布式模式让业务更高效、更安全、更稳定

​&#x1f308; 个人主页&#xff1a;danci_ &#x1f525; 系列专栏&#xff1a;《设计模式》 &#x1f4aa;&#x1f3fb; 制定明确可量化的目标&#xff0c;坚持默默的做事。 ✨欢迎加入探索分布式模式之旅✨ 在数字化时代&#xff0c;企业面临着前所未有的挑战和机遇。…

机器学习-K近邻算法(KNN)

目录 什么是KNN算法 图解KNN基本算法 &#xff08;1&#xff09;k近邻算法中k的选取 &#xff08;2&#xff09;距离函数 &#xff08;3&#xff09;归一化处理 &#xff08;4&#xff09;概率kNN KNN算法的优缺点 优势 缺点 KNN算法总结 什么是KNN算法 k近邻算法&…

vs 2022 Xamarin 生成 Android apk

再保存&#xff0c;如果没有生成apk就重启软件 再试一次

(论文阅读-优化器)Volcano-An Extensible and Parallel Query Evaluation System

目录 摘要 一、简介 三、火山模型系统设计 3.1 文件系统 3.2 查询处理 四、扩展性 五、动态查询评估计划 六、多处理器查询评估 6.1 垂直并行化 6.2 水平并行化Horizontal 6.3 exchange operator的变体 6.4 文件系统修改 七、总结 摘要 火山模型Volcano在数据库查…