【JAVA】抽象类与接口:设计模式中的应用对比(16)

核心知识点详细解释

Java抽象类和接口的定义、特点和使用场景

抽象类

抽象类是使用 abstract 关键字修饰的类。它不能被实例化,主要用于作为其他类的基类,提供一些通用的属性和方法。抽象类可以包含抽象方法和具体方法。抽象方法是使用 abstract 关键字修饰的方法,它只有方法声明,没有方法体,子类必须实现这些抽象方法。例如:

abstract class Shape {protected String color;public Shape(String color) {this.color = color;}public String getColor() {return color;}public abstract double area();
}

在这个例子中,Shape 是一个抽象类,包含一个具体方法 getColor 和一个抽象方法 area

接口

接口是一种完全抽象的类型,使用 interface 关键字定义。接口中只能包含常量和抽象方法,不能包含具体方法(Java 8 及以后版本支持默认方法和静态方法)。接口中的方法默认是 public abstract 的,常量默认是 public static final 的。例如:

interface Drawable {void draw();
}

在这个例子中,Drawable 是一个接口,包含一个抽象方法 draw

抽象类和接口在设计模式中的应用对比

策略模式

策略模式是一种行为设计模式,它定义了一系列的算法,并将每个算法封装起来,使它们可以相互替换。抽象类和接口都可以用于实现策略模式。

  • 使用抽象类实现
abstract class Strategy {public abstract void execute();
}class ConcreteStrategyA extends Strategy {@Overridepublic void execute() {System.out.println("Executing strategy A");}
}class ConcreteStrategyB extends Strategy {@Overridepublic void execute() {System.out.println("Executing strategy B");}
}class Context {private Strategy strategy;public Context(Strategy strategy) {this.strategy = strategy;}public void executeStrategy() {strategy.execute();}
}
  • 使用接口实现
interface Strategy {void execute();
}class ConcreteStrategyA implements Strategy {@Overridepublic void execute() {System.out.println("Executing strategy A");}
}class ConcreteStrategyB implements Strategy {@Overridepublic void execute() {System.out.println("Executing strategy B");}
}class Context {private Strategy strategy;public Context(Strategy strategy) {this.strategy = strategy;}public void executeStrategy() {strategy.execute();}
}

在策略模式中,使用抽象类和接口的区别不大,主要取决于具体的需求。如果需要提供一些通用的实现和属性,使用抽象类更合适;如果只需要定义行为规范,使用接口更合适。

工厂模式

工厂模式是一种创建型设计模式,它提供了一种创建对象的方式,将对象的创建和使用分离。抽象类和接口都可以用于实现工厂模式。

  • 使用抽象类实现
abstract class Product {public abstract void use();
}class ConcreteProductA extends Product {@Overridepublic void use() {System.out.println("Using product A");}
}class ConcreteProductB extends Product {@Overridepublic void use() {System.out.println("Using product B");}
}abstract class Factory {public abstract Product createProduct();
}class ConcreteFactoryA extends Factory {@Overridepublic Product createProduct() {return new ConcreteProductA();}
}class ConcreteFactoryB extends Factory {@Overridepublic Product createProduct() {return new ConcreteProductB();}
}
  • 使用接口实现
interface Product {void use();
}class ConcreteProductA implements Product {@Overridepublic void use() {System.out.println("Using product A");}
}class ConcreteProductB implements Product {@Overridepublic void use() {System.out.println("Using product B");}
}interface Factory {Product createProduct();
}class ConcreteFactoryA implements Factory {@Overridepublic Product createProduct() {return new ConcreteProductA();}
}class ConcreteFactoryB implements Factory {@Overridepublic Product createProduct() {return new ConcreteProductB();}
}

在工厂模式中,使用抽象类和接口的选择也取决于具体需求。如果需要提供一些通用的创建逻辑,使用抽象类更合适;如果只需要定义创建对象的规范,使用接口更合适。

根据具体需求选择抽象类或接口

  • 需要提供通用实现:如果需要提供一些通用的属性和方法实现,使用抽象类。抽象类可以包含具体方法,子类可以继承这些方法,避免重复实现。
  • 只需要定义行为规范:如果只需要定义一组行为规范,不关心具体实现,使用接口。接口可以让一个类实现多个接口,实现多重继承的效果。
  • 单继承限制:由于 Java 是单继承的,一个类只能继承一个抽象类。如果一个类已经继承了某个类,但还需要实现其他行为规范,使用接口。

实际业务场景中的应用案例

图形绘制系统

在一个图形绘制系统中,可以使用抽象类 Shape 来定义图形的通用属性和方法,如颜色、面积计算等。然后使用接口 Drawable 来定义图形的绘制行为。不同的图形类可以继承 Shape 类并实现 Drawable 接口。例如:

abstract class Shape {protected String color;public Shape(String color) {this.color = color;}public String getColor() {return color;}public abstract double area();
}interface Drawable {void draw();
}class Circle extends Shape implements Drawable {private double radius;public Circle(String color, double radius) {super(color);this.radius = radius;}@Overridepublic double area() {return Math.PI * radius * radius;}@Overridepublic void draw() {System.out.println("Drawing a circle with color " + getColor());}
}

电商系统中的折扣策略

在电商系统中,可以使用接口来定义折扣策略。不同的折扣策略类实现该接口,提供不同的折扣计算方法。例如:

interface DiscountStrategy {double calculateDiscount(double price);
}class PercentageDiscount implements DiscountStrategy {private double percentage;public PercentageDiscount(double percentage) {this.percentage = percentage;}@Overridepublic double calculateDiscount(double price) {return price * percentage / 100;}
}class FixedAmountDiscount implements DiscountStrategy {private double amount;public FixedAmountDiscount(double amount) {this.amount = amount;}@Overridepublic double calculateDiscount(double price) {return amount;}
}

常见面试问题与解答思路

问题 1:抽象类和接口的区别是什么?

解答思路:抽象类可以包含具体方法和抽象方法,而接口在 Java 8 之前只能包含抽象方法(Java 8 及以后支持默认方法和静态方法);抽象类使用 abstract 关键字定义,接口使用 interface 关键字定义;一个类只能继承一个抽象类,但可以实现多个接口;抽象类可以有构造方法,接口没有构造方法。

问题 2:在什么情况下应该使用抽象类,什么情况下应该使用接口?

解答思路:如果需要提供通用的实现和属性,使用抽象类;如果只需要定义行为规范,使用接口;如果一个类已经继承了某个类,但还需要实现其他行为规范,使用接口。

问题 3:如何在 Java 中实现多重继承的效果?

解答思路:由于 Java 是单继承的,一个类只能继承一个父类。但可以通过实现多个接口来实现多重继承的效果。一个类可以实现多个接口,从而拥有多个接口定义的行为。

相关技术点的性能优化建议

避免过度使用抽象类和接口

虽然抽象类和接口可以提高代码的灵活性和可维护性,但过度使用会增加代码的复杂度。在设计时,要根据实际需求合理使用抽象类和接口。

优化接口设计

接口的设计应该遵循单一职责原则,每个接口只负责一个特定的功能。避免设计过大的接口,导致实现类需要实现很多不必要的方法。

合理使用默认方法和静态方法

在 Java 8 及以后版本中,接口支持默认方法和静态方法。合理使用这些方法可以减少代码的重复,但也要注意不要滥用,以免破坏接口的纯粹性。

扩展学习资源推荐

官方文档

  • Oracle Java Documentation:提供了 Java 语言和类库的详细文档。
  • The Java Tutorials:适合初学者学习 Java 的基础知识,包括抽象类和接口的内容。

书籍

  • 《Effective Java》:介绍了 Java 编程的最佳实践和技巧,对抽象类和接口的使用有相关建议。
  • 《Java核心技术》:详细讲解了 Java 语言的基础知识和高级特性,包含了抽象类和接口的核心概念。

思考题

  1. 抽象类可以有静态方法吗?如果可以,有什么作用?
  2. 接口中的默认方法和抽象方法有什么区别?
  3. 如何在一个类中同时继承抽象类和实现接口?

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

HTML 颜色全解析:从命名规则到 RGBA/HSL 值,附透明度设置与场景应用指南

一、HTML 颜色系统详解 HTML 中的颜色可以通过多种方式定义,包括颜色名称、RGB 值、十六进制值、HSL 值等,同时支持透明度调整。以下是详细分类及应用场景: 1. 颜色名称(预定义关键字) HTML 预定义了 140 个标准颜色名…

LVS负载均衡群集和keepalive

目录 一. 集群概述 1.1 集群的定义 1.2 集群的分类 1. 高可用集群 HA 2. 高性能运输群集 HPC 3.负载均衡群集 LB 4. 分布式存储集群 二. LVS概述 2.1 LVS的定义 2.2 LVS的工作原理 2.3 LVS 的三种工作模式 2.4 LVS 三种工作模式的对比 2.5 LVS 调度算法 1. 静态…

ZTE 7551N 中兴小鲜60 远航60 努比亚小牛 解锁BL 刷机包 刷root 展讯 T760 bl

ZTE 7551N 中兴小鲜60 远航60 努比亚小牛 解锁BL 刷机包 刷root 3款机型是一个型号,包通用, ro.product.system.modelZTE 7551N ro.product.system.nameCN_P720S15 #################################### # from generate-common-build-props # Th…

单片机-STM32部分:12、I2C

飞书文档https://x509p6c8to.feishu.cn/wiki/MsB7wLebki07eUkAZ1ec12W3nsh 一、简介 IIC协议,又称I2C协议,是由PHILP公司在80年代开发的两线式串行总线,用于连接微控制器及其外围设备,IIC属于半双工同步通信方式。 IIC是一种同步…

Virtualized Table 虚拟化表格 el-table-v2 表头分组 多级表头的简单示例

注意添加这个属性,会影响到有多少个层级的表头: :header-height“[50, 40]”,即后面的columnIndex 如果有fix的列CustomizedHeader会被调用多次,如果有多个层级的表头,也会被调用多次, 实际被调用次数是(fix数 1 * 表头层级数量) 以下代码均删除了JSX TS版本代码 <templ…

防御保护-----第十二章:VPN概述

文章目录 第二部分&#xff0c;数据安全第十二章&#xff1a;VPN概述VPN概述VPN分类VPN关键技术隧道技术身份认证技术加解密技术数据认证技术 数据的安全传输密码学发展史 对称加密算法 --- 传统密码算法密钥解释流加密分组加密 --- 块加密算法填充算法PKCS7算法分组模式 公钥密…

前端项目打包部署流程j

1.打包前端项目(运行build这个文件) 2.打包完成后&#xff0c;控制台如下所示:(没有报错即代表成功) 3.左侧出现dist文件夹 4.准备好我们下载的nginx(可以到官网下载一个),然后在一个没有中文路径下的文件夹里面解压。 5.在继承终端内打开我们的项目&#xff0c;找到前面打包好…

Go语言标识符

文章目录 标识符的组成规则Go语言关键字预定义标识符标识符命名惯例 特殊标识符标识符访问权限控制 在Go语言中&#xff0c;标识符(Identifier)是用来命名变量、函数、类型、常量等程序实体的名称。 标识符的组成规则 1、必须以字母或下划线(_)开头&#xff1a; 字母包括Unico…

CST软件对OPERACST软件联合仿真汽车无线充电站对人体的影响

上海又收紧了新能源车的免费上牌政策。所以年前一些伙伴和我探讨过买新能源汽车的问题&#xff0c;小伙伴们基本纠结的点是买插电还是纯电&#xff1f;我个人是很抗拒新能源车的&#xff0c;也开过坐过。个人有几个观点&#xff1a; 溢价过高&#xff0c;不保值。实际并不环保…

吴恩达机器学习笔记:多变量梯度下降

1.多维特征 之前我们探讨了单变量/特征的回归模型&#xff0c;现在我们对房价模型增加更多的特征&#xff0c;例如房间数楼层等&#xff0c;构成一个含有多个变量的模型&#xff0c;模型中的特征为 &#xff08; x 1 &#xff0c; x 2 &#xff0c; x 3... x n &#xff09; &…

【Linux Nano Vim快捷键大全】

Nano 快捷键大全 常用高频操作 功能描述快捷键组合替代按键/备注使用频率显示帮助CtrlGF1高保存文件CtrlOF3高退出编辑器CtrlXF2高剪切当前行CtrlKF9高粘贴内容CtrlUF10高搜索文本CtrlWF6高替换文本Ctrl\AltR高撤销操作AltU无中重做操作AltE无中跳转到行号Ctrl_AltG中插入文件…

uniapp vue 沉浸式窗体如何获取并排除外部手机浏览器底部菜单栏工具栏高度

这个问题可以简称为&#xff1a;uniapp vue 获取可视窗口高度 第一种方案&#xff0c;只改变css样式 /* 不考虑浏览器UI的最小视口高度 */ .element {height: 100svh; /* small viewport height */ }/* 考虑浏览器UI变化的动态视口高度 */ .element {height: 100dvh; /* dyna…

React Native告别图标体积大手动更换慢的噩梦:让图标更新像修改文字一样简单

写在前面:凌晨三点的图标战争 “所有图标都要换成圆角风格,明天上线!”——产品经理这条消息弹出时,我的保温杯差点从手中滑落。扫了一眼项目中的347个图标文件,我知道今晚又是个不眠夜。但就在绝望之际,同事发来一个GIF:他只是在终端输入了iconfont-rn --update,所有…

自然语言处理与BI融合实战:ChatBI动态语义解析技术架构剖析

在数字经济时代&#xff0c;数据已成为企业核心竞争力的关键要素。如何高效挖掘数据价值、实现智能化决策&#xff0c;成为企业数字化转型的核心命题。传统商业智能&#xff08;BI&#xff09;工具虽具备强大的数据处理能力&#xff0c;但其技术门槛高、交互方式复杂等局限性日…

鸿蒙OSUniApp开发支持多语言的国际化组件#三方框架 #Uniapp

使用UniApp开发支持多语言的国际化组件 在全球化的今天&#xff0c;一个优秀的应用往往需要支持多种语言以满足不同地区用户的需求。本文将详细讲解如何在UniApp框架中实现一套完整的国际化解决方案&#xff0c;从而轻松实现多语言切换功能。 前言 去年接手了一个面向国际市场…

SpringBoot的外部化配置

一、什么是外部化配置 外部化配置是指把应用程序中各种可配置的参数、属性等信息&#xff0c;从代码内部提取出来&#xff0c;放置在外部的配置文件、数据库或配置中心等地方&#xff08;比如使用.properties、.yml 或.xml 等格式的文件&#xff09;进行管理。提高应用程序的可…

SQL中联表的运用

当出现要大量数据去查询时&#xff0c;不要一个个去SQL查询&#xff0c;应该要批量的去查询。 def batch_cavity_query(self, fuseids): “”“批量查询cavity信息”“” if not fuseids: return {} # 创建临时表批量查询 try:# 创建临时表self.cursor.execute("CREATE …

React面试常问问题详解

以下是30个React面试中常见的问题及简要解析&#xff0c;涵盖基础概念、核心原理、性能优化、Hooks、状态管理等方面&#xff0c;适用于初中高级开发者准备面试时参考&#xff1a; 一、React 基础与核心概念 React 是什么&#xff1f; React 是由 Facebook 开发的用于构建用户界…

【vite好用的配置】自动导入组件、vue中的hook、路径解析、打包配置、本地运行反向代理配置

前言 之前出了一篇自己搭建 后台管理系统的文章&#xff0c;今天顺便把vite配置&#xff0c;涉及到的一些给大家分享吧。 按需食用哈。 文章目录 前言一、 自动导入vue中的hook、ref等1. 安装插件2. 配置 Vite&#xff08;vite.config.ts 或 vite.config.js&#xff09;1&…

思科(Cisco ASA/Firepower)、华三(H3C)、华为(Huawei USG)防火墙 的基础配置

以下是针对 思科&#xff08;Cisco ASA/Firepower&#xff09;、华三&#xff08;H3C&#xff09;、华为&#xff08;Huawei USG&#xff09;防火墙 的基础配置指南&#xff0c;涵盖 区域划分、安全策略、NAT、路由 等核心功能。配置示例基于通用场景&#xff0c;实际部署时需根…