当前位置: 首页 > news >正文

主要的软件设计模式及其在Kotlin中的实现示例

软件设计模式(Software Design Patterns)是面向对象设计中常用的解决方案,它们为常见的软件设计问题提供了一些被证明有效的解决方案。以下是一些主要的软件设计模式及其在Kotlin中的实现示例。

创建型模式(Creational Patterns)

单例模式(Singleton Pattern)

确保一个类只有一个实例,并提供全局访问点。

object Singleton {init {println("Singleton instance created")}fun doSomething() {println("Doing something")}
}// 使用
fun main() {Singleton.doSomething()
}
工厂模式(Factory Pattern)

定义一个创建对象的接口,但由子类决定要实例化的类。

interface Product {fun use()
}class ConcreteProductA : Product {override fun use() {println("Using Product A")}
}class ConcreteProductB : Product {override fun use() {println("Using Product B")}
}class ProductFactory {fun createProduct(type: String): Product {return when (type) {"A" -> ConcreteProductA()"B" -> ConcreteProductB()else -> throw IllegalArgumentException("Unknown product type")}}
}// 使用
fun main() {val factory = ProductFactory()val productA = factory.createProduct("A")productA.use()val productB = factory.createProduct("B")productB.use()
}
抽象工厂模式(Abstract Factory Pattern)

提供一个接口,用于创建相关或依赖对象的家族,而不需要指定具体类。

interface Button {fun click()
}class WindowsButton : Button {override fun click() {println("Windows Button clicked")}
}class MacButton : Button {override fun click() {println("Mac Button clicked")}
}interface GUIFactory {fun createButton(): Button
}class WindowsFactory : GUIFactory {override fun createButton(): Button {return WindowsButton()}
}class MacFactory : GUIFactory {override fun createButton(): Button {return MacButton()}
}// 使用
fun main() {val factory: GUIFactory = WindowsFactory()val button = factory.createButton()button.click()
}
建造者模式(Builder Pattern)

将一个复杂对象的构建与其表示分离,使得同样的构建过程可以创建不同的表示。

class Product private constructor(builder: Builder) {val partA: String?val partB: String?val partC: String?init {partA = builder.partApartB = builder.partBpartC = builder.partC}class Builder {var partA: String? = nullprivate setvar partB: String? = nullprivate setvar partC: String? = nullprivate setfun setPartA(partA: String) = apply { this.partA = partA }fun setPartB(partB: String) = apply { this.partB = partB }fun setPartC(partC: String) = apply { this.partC = partC }fun build() = Product(this)}
}// 使用
fun main() {val product = Product.Builder().setPartA("A").setPartB("B").setPartC("C").build()println("Product parts: ${product.partA}, ${product.partB}, ${product.partC}")
}

结构型模式(Structural Patterns)

适配器模式(Adapter Pattern)

将一个类的接口转换成客户希望的另一个接口,使得原本由于接口不兼容而不能一起工作的类可以协同工作。

interface Target {fun request()
}class Adaptee {fun specificRequest() {println("Specific request")}
}class Adapter(private val adaptee: Adaptee) : Target {override fun request() {adaptee.specificRequest()}
}// 使用
fun main() {val adaptee = Adaptee()val adapter = Adapter(adaptee)adapter.request()
}
装饰器模式(Decorator Pattern)

动态地将责任附加到对象上,提供了一种灵活替代继承的方法来扩展功能。

interface Component {fun operation()
}class ConcreteComponent : Component {override fun operation() {println("Concrete Component operation")}
}open class Decorator(private val component: Component) : Component {override fun operation() {component.operation()}
}class ConcreteDecorator(component: Component) : Decorator(component) {override fun operation() {super.operation()addedBehavior()}private fun addedBehavior() {println("Added behavior")}
}// 使用
fun main() {val component: Component = ConcreteDecorator(ConcreteComponent())component.operation()
}
代理模式(Proxy Pattern)

为另一个对象提供一个代理以控制对这个对象的访问。

interface Subject {fun request()
}class RealSubject : Subject {override fun request() {println("RealSubject request")}
}class Proxy(private val realSubject: RealSubject) : Subject {override fun request() {println("Proxy request")realSubject.request()}
}// 使用
fun main() {val realSubject = RealSubject()val proxy = Proxy(realSubject)proxy.request()
}
外观模式(Facade Pattern)

为子系统中的一组接口提供一个一致的界面,使得子系统更容易使用。

class SubsystemA {fun operationA() {println("Subsystem A operation")}
}class SubsystemB {fun operationB() {println("Subsystem B operation")}
}class Facade {private val subsystemA = SubsystemA()private val subsystemB = SubsystemB()fun operation() {subsystemA.operationA()subsystemB.operationB()}
}// 使用
fun main() {val facade = Facade()facade.operation()
}

行为型模式(Behavioral Patterns)

策略模式(Strategy Pattern)

定义一系列算法,把它们一个个封装起来,并且使它们可以相互替换。

interface Strategy {fun execute()
}class ConcreteStrategyA : Strategy {override fun execute() {println("Executing Strategy A")}
}class ConcreteStrategyB : Strategy {override fun execute() {println("Executing Strategy B")}
}class Context(private var strategy: Strategy) {fun setStrategy(strategy: Strategy) {this.strategy = strategy}fun executeStrategy() {strategy.execute()}
}// 使用
fun main() {val context = Context(ConcreteStrategyA())context.executeStrategy()context.setStrategy(ConcreteStrategyB())context.executeStrategy()
}
观察者模式(Observer Pattern)

定义对象间的一种一对多的依赖关系,以便当一个对象的状态发生改变时,所有依赖于它的对象都会得到通知并自动更新。

interface Observer {fun update()
}class ConcreteObserver : Observer {override fun update() {println("Observer updated")}
}class Subject {private val observers = mutableListOf<Observer>()fun addObserver(observer: Observer) {observers.add(observer)}fun removeObserver(observer: Observer) {observers.remove(observer)}fun notifyObservers() {for (observer in observers) {observer.update()}}
}// 使用
fun main() {val subject = Subject()val observer = ConcreteObserver()subject.addObserver(observer)subject.notifyObservers()subject.removeObserver(observer)subject.notifyObservers()
}
命令模式(Command Pattern)

将请求封装成对象,从而使得您可以用不同的请求对客户进行参数化。

interface Command {fun execute()
}class ConcreteCommand(private val receiver: Receiver) : Command {override fun execute() {receiver.action()}
}class Receiver {fun action() {println("Receiver action")}
}class Invoker {private lateinit var command: Commandfun setCommand(command: Command) {this.command = command}fun executeCommand() {command.execute()}
}// 使用
fun main() {val receiver = Receiver()val command = ConcreteCommand(receiver)val invoker = Invoker()invoker.setCommand(command)invoker.executeCommand()
}
责任链模式(Chain of Responsibility Pattern)

使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合。

abstract class Handler {var nextHandler: Handler? = nullfun handleRequest(request: String) {if (canHandle(request)) {process(request)} else {nextHandler?.handleRequest(request)}}protected abstract fun canHandle(request: String): Booleanprotected abstract fun process(request: String)
}class ConcreteHandlerA : Handler() {override fun canHandle(request: String) = request == "A"override fun process(request: String) {println("Handler A processed $request")}
}class ConcreteHandlerB : Handler(){override fun canHandle(request: String) = request == "B"override fun process(request: String) {println("Handler B processed $request")}
}// 使用
fun main() {val handlerA = ConcreteHandlerA()val handlerB = ConcreteHandlerB()handlerA.nextHandler = handlerBhandlerA.handleRequest("A")handlerA.handleRequest("B")
}

这些示例展示了Kotlin中如何实现一些常见的设计模式。每个模式都有其特定的用途和场景,选择适合的模式可以大大提升代码的可维护性和扩展性。

我有多年软件开发经验,精通嵌入式STM32,RTOS,Linux,Ubuntu, Android AOSP, Android APP, Java , Kotlin , C, C++, Python , QT。 如果您有软件开发定制需求,请联系我,电子邮件: mysolution@qq.com

相关文章:

主要的软件设计模式及其在Kotlin中的实现示例

软件设计模式&#xff08;Software Design Patterns&#xff09;是面向对象设计中常用的解决方案&#xff0c;它们为常见的软件设计问题提供了一些被证明有效的解决方案。以下是一些主要的软件设计模式及其在Kotlin中的实现示例。 创建型模式&#xff08;Creational Patterns&…...

FFmpeg音频重采样基本流程

目录 流程概述用到的APItipsdemo样例附录 - SwrContext结构体字段 流程概述 音频重采样的基本流程为&#xff1a; 申请重采样器上下文设置重采样去上下文的参数初始化重采样器申请数据存放的缓冲区空间进行重采样 注意&#xff0c;要先设置参数再对重采样器初始化 用到的API…...

无人机无人车固态锂电池技术详解

随着无人机和无人车技术的飞速发展&#xff0c;对高性能、高安全性电池的需求日益迫切。固态锂电池作为下一代电池技术的代表&#xff0c;正逐步从实验室走向市场&#xff0c;为无人机和无人车等应用领域带来革命性的变化。相比传统液态锂电池&#xff0c;固态锂电池在能量密度…...

ElementUI元件库在Axure中使用

一、ElementUI元件库介绍 ElementUI 是一套为开发者、UI/UX设计师和产品经理准备的基于Vue 2.0的桌面端组件库。它以其优雅的设计和丰富的组件&#xff0c;极大地提升了Web应用的开发效率与用户体验。ElementUI的组件设计精致且符合现代UI规范&#xff0c;包括按钮、表单、弹窗…...

联想M7615DNA打印机复印证件太黑的解决方法及个人建议

打印机在使用过程中&#xff0c;可能会出现复印的文字或图片太黑的问题&#xff0c;这会影响到打印或复印的效果。下面我们来了解一下这种情况的原因和解决方法&#xff1b;以下所述操作仅供大家参考&#xff0c;如有不足请大家提出宝贵意见&#xff1b; 证件包括&#xff1a;…...

【算法题】无重复字符的最长子串(滑动窗口)

目录 一、题目描述 二、解题思路 1、什么是滑动窗口算法&#xff1f; 2、滑动窗口一般解题模板 三、参考答案 一、题目描述 无重复字符的最长子串 给定一个字符串s &#xff0c;请你找出其中不含有重复字符的最长子串的长度。 示例 1: 输入: s "abcabcbb"…...

Hikari连接池 最大连接数与最小空闲连接数配置多少合适?

spring:datasource: # 数据源的相关配置type: com.zaxxer.hikari.HikariDataSource # 数据源类型&#xff1a;HikariCPdriver-class-name: com.mysql.jdbc.Driver # mysql驱动url: jdbc:mysql://localhost:3306/t…...

【2.4 python中的基本输入和输出】

2.4 python中的基本输入和输出 在Python中&#xff0c;基本输入和输出是通过内置的input()函数和print()函数来实现的。这两个函数提供了与用户或其他程序进行交互的基本方式。 1. input() 函数 input() 函数用于从标准输入设备&#xff08;通常是键盘&#xff09;接收一行文…...

netty长连接集群方案

背景 公司某拍卖系统使用的netty服务不支持集群部署,不能进行横向扩展;并且和用户聚合服务耦合在一起,服务多节点部署不能提高拍卖性能,不能支撑更多用户使用拍卖。 目前需要改造并出一个集群的方案。 思路 因为是长连接的服务做集群,需要我们在客户端和服务器建立链接…...

Python面试题:结合Python技术,如何使用Keras进行神经网络建模

使用Keras进行神经网络建模是机器学习和深度学习领域中常用的方法之一。Keras是一个高级神经网络API&#xff0c;能够在TensorFlow、Theano等后端上运行&#xff0c;提供了简单易用的接口。下面是使用Keras进行神经网络建模的基本步骤&#xff1a; 安装Keras Keras是集成在Te…...

dll文件丢失怎么恢复?超简单的5个方法,1分钟搞定dll文件修复!

DLL&#xff0c;或称动态链接库&#xff0c;是一种重要的文件类型&#xff0c;包含了一系列用于运行几乎所有程序的指令&#xff0c;这些程序在win11、win10、win8和win7系统中都广泛使用。如果Windows操作系统中的dll文件丢失&#xff0c;您可能无法正常启动所需的程序或应用。…...

[Meachines] [Easy] Sense PFSense防火墙RCE

信息收集 IP AddressOpening Ports10.10.10.60TCP:80,443 $ nmap -p- 10.10.10.60 --min-rate 1000 -sC -sV PORT STATE SERVICE VERSION 80/tcp open http lighttpd 1.4.35 |_http-title: Did not follow redirect to https://10.10.10.60/ |_http-server-header…...

codetop标签双指针题目大全解析(C++解法),双指针刷穿地心!!!

写在前面&#xff1a;此篇博客是以[双指针总结]博客为基础的针对性训练&#xff0c;题源是codetop标签双指针近一年&#xff0c;频率由高到低 1.无重复字符的最长子串2.三数之和3.环形链表4.合并两个有序数组5.接雨水6.环形链表II7.删除链表的倒数第N个节点8.训练计划II9.最小覆…...

Floyd求最短路

给定一个 nn 个点 mm 条边的有向图&#xff0c;图中可能存在重边和自环&#xff0c;边权可能为负数。 再给定 kk 个询问&#xff0c;每个询问包含两个整数 xx 和 yy&#xff0c;表示查询从点 xx 到点 yy 的最短距离&#xff0c;如果路径不存在&#xff0c;则输出 impossible。…...

python爬虫初识

一、什么互联网 互联网&#xff08;Internet&#xff09;是全球范围内最大的计算机网络&#xff0c;它将数以百万计的私人、公共、学术、商业和政府网络通过一系列标准通信协议&#xff08;如TCP/IP&#xff09;连接起来形成的一个庞大的国际网络。 互联网的起源可以追溯到196…...

Java中类的构造

1.私有化成员变量。 2.空参构造方法。 3.带全部参数的构造方法。 4.get / set方法。 package demo;public class student{//1.私有化成员变量。//2.空参构造方法。//3.带全部参数的构造方法。//4.get / set方法。private String name;private int age;public student() {}pu…...

【C++高阶】深入理解C++异常处理机制:从try到catch的全面解析

&#x1f4dd;个人主页&#x1f339;&#xff1a;Eternity._ ⏩收录专栏⏪&#xff1a;C “ 登神长阶 ” &#x1f921;往期回顾&#x1f921;&#xff1a;Lambda表达式 &#x1f339;&#x1f339;期待您的关注 &#x1f339;&#x1f339; ❀C异常 &#x1f4d2;1. C异常概念…...

【RHEL7】无人值守安装系统

目录 一、kickstart服务 1.下载kickstart 2.启动图形制作工具 3.选择设置 4.查看生成的文件 5.修改ks.cfg文件 二、HTTP服务 1.下载HTTP服务 2.启动HTTP服务 3.将挂载文件和ks.cfg放在HTTP默认目录下 4.测试HTTP服务 三、PXE 1.查看pxe需要安装什么 2.安装 四、…...

[RTOS 学习记录] 预备知识:C语言结构体

这篇文章是我阅读《嵌入式实时操作系统μCOS-II原理及应用》后的读书笔记&#xff0c;记录目的是为了个人后续回顾复习使用。 文章目录 结构体结构体基础声明和定义结构体类型声明和定义结构体变量初始化结构体变量初始化各个成员使用列表符号初始化 使用结构体变量综上 结构体…...

sqli-labs注入漏洞解析--less-9/10

第九关&#xff1a; 这一关相比第八关&#xff0c;第八关他正确显示you are in,错误不显示you are in,但是第九关你不管是输入正确或者错误都显示 you are in &#xff0c;这个时候布尔盲注就不适合我们用&#xff0c;所以我们的换一下思路,布尔盲注适合页面对于错误和正确结果…...

观成科技:隐蔽隧道工具Ligolo-ng加密流量分析

1.工具介绍 Ligolo-ng是一款由go编写的高效隧道工具&#xff0c;该工具基于TUN接口实现其功能&#xff0c;利用反向TCP/TLS连接建立一条隐蔽的通信信道&#xff0c;支持使用Let’s Encrypt自动生成证书。Ligolo-ng的通信隐蔽性体现在其支持多种连接方式&#xff0c;适应复杂网…...

【JavaEE】-- HTTP

1. HTTP是什么&#xff1f; HTTP&#xff08;全称为"超文本传输协议"&#xff09;是一种应用非常广泛的应用层协议&#xff0c;HTTP是基于TCP协议的一种应用层协议。 应用层协议&#xff1a;是计算机网络协议栈中最高层的协议&#xff0c;它定义了运行在不同主机上…...

Docker 本地安装 mysql 数据库

Docker: Accelerated Container Application Development 下载对应操作系统版本的 docker &#xff1b;并安装。 基础操作不再赘述。 打开 macOS 终端&#xff0c;开始 docker 安装mysql之旅 第一步 docker search mysql 》〉docker search mysql NAME DE…...

七、数据库的完整性

七、数据库的完整性 主要内容 7.1 数据库的完整性概述 7.2 实体完整性 7.3 参照完整性 7.4 用户定义的完整性 7.5 触发器 7.6 SQL Server中数据库完整性的实现 7.7 小结 7.1 数据库的完整性概述 数据库完整性的含义 正确性 指数据的合法性 有效性 指数据是否属于所定…...

为什么要创建 Vue 实例

核心原因:Vue 需要一个「控制中心」来驱动整个应用 你可以把 Vue 实例想象成你应用的**「大脑」或「引擎」。它负责协调模板、数据、逻辑和行为,将它们变成一个活的、可交互的应用**。没有这个实例,你的代码只是一堆静态的 HTML、JavaScript 变量和函数,无法「活」起来。 …...

LOOI机器人的技术实现解析:从手势识别到边缘检测

LOOI机器人作为一款创新的AI硬件产品&#xff0c;通过将智能手机转变为具有情感交互能力的桌面机器人&#xff0c;展示了前沿AI技术与传统硬件设计的完美结合。作为AI与玩具领域的专家&#xff0c;我将全面解析LOOI的技术实现架构&#xff0c;特别是其手势识别、物体识别和环境…...

Python网页自动化Selenium中文文档

1. 安装 1.1. 安装 Selenium Python bindings 提供了一个简单的API&#xff0c;让你使用Selenium WebDriver来编写功能/校验测试。 通过Selenium Python的API&#xff0c;你可以非常直观的使用Selenium WebDriver的所有功能。 Selenium Python bindings 使用非常简洁方便的A…...

FFmpeg avformat_open_input函数分析

函数内部的总体流程如下&#xff1a; avformat_open_input 精简后的代码如下&#xff1a; int avformat_open_input(AVFormatContext **ps, const char *filename,ff_const59 AVInputFormat *fmt, AVDictionary **options) {AVFormatContext *s *ps;int i, ret 0;AVDictio…...

Python训练营-Day26-函数专题1:函数定义与参数

题目1&#xff1a;计算圆的面积 任务&#xff1a; 编写一个名为 calculate_circle_area 的函数&#xff0c;该函数接收圆的半径 radius 作为参数&#xff0c;并返回圆的面积。圆的面积 π * radius (可以使用 math.pi 作为 π 的值)要求&#xff1a;函数接收一个位置参数 radi…...

LangChain 中的文档加载器(Loader)与文本切分器(Splitter)详解《二》

&#x1f9e0; LangChain 中 TextSplitter 的使用详解&#xff1a;从基础到进阶&#xff08;附代码&#xff09; 一、前言 在处理大规模文本数据时&#xff0c;特别是在构建知识库或进行大模型训练与推理时&#xff0c;文本切分&#xff08;Text Splitting&#xff09; 是一个…...