Go和Java实现装饰器模式

Go和Java实现装饰器模式

我们通过人穿着打扮自己的实例来演示装饰器模式的用法。

1、装饰器模式

装饰器模式允许向一个现有的对象添加新的功能,同时又不改变其结构。这种类型的设计模式属于结构型模式,它

是作为现有的类的一个包装。

装饰器模式通过将对象包装在装饰器类中,以便动态地修改其行为。

这种模式创建了一个装饰类,用来包装原有的类,并在保持类方法签名完整性的前提下,提供了额外的功能。

  • 意图:动态地给一个对象添加一些额外的职责。就增加功能来说,装饰器模式相比生成子类更为灵活。

  • 主要解决:一般的,我们为了扩展一个类经常使用继承方式实现,由于继承为类引入静态特征,并且随着扩展

    功能的增多,子类会很膨胀。

  • 何时使用:在不想增加很多子类的情况下扩展类。

  • 如何解决:将具体功能职责划分,同时继承装饰者模式。

  • 关键代码:1、Component 类充当抽象角色,不应该具体实现。 2、修饰类引用和继承 Component 类,具

    体扩展类重写父类方法。

  • 应用实例:1、孙悟空有 72 变,当他变成"庙宇"后,他的根本还是一只猴子,但是他又有了庙宇的功能。 2、

    不论一幅画有没有画框都可以挂在墙上,但是通常都是有画框的,并且实际上是画框被挂在墙上。在挂在墙上

    之前,画可以被蒙上玻璃,装到框子里;这时画、玻璃和画框形成了一个物体。

  • 优点:装饰类和被装饰类可以独立发展,不会相互耦合,装饰模式是继承的一个替代模式,装饰模式可以动态

    扩展一个实现类的功能。

  • 缺点:多层装饰比较复杂。

  • 使用场景:1、扩展一个类的功能。 2、动态增加功能,动态撤销。

  • 注意事项:可代替继承。

  • 装饰器模式包含以下几个核心角色:

    抽象组件(Component):定义了原始对象和装饰器对象的公共接口或抽象类,可以是具体组件类的父类或

    接口。

    具体组件(Concrete Component):是被装饰的原始对象,它定义了需要添加新功能的对象。

    抽象装饰器(Decorator):继承自抽象组件,它包含了一个抽象组件对象,并定义了与抽象组件相同的接

    口,同时可以通过组合方式持有其他装饰器对象。

    具体装饰器(Concrete Decorator):实现了抽象装饰器的接口,负责向抽象组件添加新的功能。具体装饰

    器通常会在调用原始对象的方法之前或之后执行自己的操作。

  • 适用性:

    在不影响其他对象的情况下,以动态、透明的方式给单个对象添加职责。

    处理那些可以撤消的职责。

    当不能采用生成子类的方法进行扩充时。

装饰器模式通过嵌套包装多个装饰器对象,可以实现多层次的功能增强。每个具体装饰器类都可以选择性地增加新

的功能,同时保持对象接口的一致性。

2、Go实现装饰器模式

package decorator// ========== Person ==========
type Person interface {// 形象展示Show()
}
package decoratorimport "fmt"// ========== 服饰类 ==========
type Finery struct {
}func (finery *Finery) Show() {fmt.Println("穿着了如下衣服:")
}
package decorator// ========== FineryDecorator =========
type FineryDecorator interface {Decorate(Person)
}
package decoratorimport "fmt"// ========== Tshirt =========
type Tshirt struct {person Person
}func (tshirt *Tshirt) Decorate(person Person) {tshirt.person = person
}func (tshirt *Tshirt) Show() {tshirt.person.Show()fmt.Println("大T恤")
}
package decoratorimport "fmt"// ========== Trouser =========
type Trouser struct {person Person
}func (trouser *Trouser) Decorate(person Person) {trouser.person = person
}func (trouser *Trouser) Show() {trouser.person.Show()fmt.Println("阔腿裤")
}
package decoratorimport "fmt"// ========== Shoe =========
type Shoe struct {person Person
}func (shoe *Shoe) Decorate(person Person) {shoe.person = person
}func (shoe *Shoe) Show() {shoe.person.Show()fmt.Println("运动鞋")
}
package mainimport . "proj/decorator"func main() {person := &Finery{}tshirt := &Tshirt{}trouser := &Trouser{}shoe := Shoe{}tshirt.Decorate(person)trouser.Decorate(tshirt)shoe.Decorate(trouser)shoe.Show()
}
# 输出
穿着了如下衣服:
大T恤
阔腿裤
运动鞋

3、Java实现装饰器模式

package com.decorator;// ========== Person ==========
public interface Person {// 形象展示void show();
}
package com.decorator;// ========== 服饰类 ==========
public class Finery implements Person{@Overridepublic void show() {System.out.println("穿着了如下衣服:");}
}
package com.decorator;// ========== FineryDecorator =========
public class FineryDecorator implements Person{protected Person person;public void decorator(Person person){this.person = person;}@Overridepublic void show() {this.person.show();}
}
package com.decorator;// ========== Tshirt =========
public class Tshirt extends FineryDecorator{@Overridepublic void show() {super.show();System.out.println("大T恤");}
}
package com.decorator;// ========== Trouser =========
public class Trouser extends FineryDecorator {@Overridepublic void show() {super.show();System.out.println("阔腿裤");}}
package com.decorator;// ========== Shoe =========
public class Shoe extends FineryDecorator{@Overridepublic void show() {super.show();System.out.println("运动鞋");}
}
package com.decorator;public class Test {public static void main(String[] args) {Person person = new Finery();FineryDecorator fineryDecorator = new FineryDecorator();Tshirt tshirt = new Tshirt();Trouser trouser = new Trouser();Shoe shoe = new Shoe();fineryDecorator.decorator(person);tshirt.decorator(fineryDecorator);trouser.decorator(tshirt);shoe.decorator(trouser);shoe.show();}
}
# 输出
穿着了如下衣服:
大T恤
阔腿裤
运动鞋

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

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

相关文章

vscode启动leiningen项目

要在 VS Code 中启动 Leiningen 项目,你可以按照以下步骤进行操作: 确保已经安装了 Leiningen。你可以在终端中输入 lein version 来检查是否已成功安装。 在 VS Code 中安装 Leiningen 扩展。打开 VS Code,点击左侧的扩展图标(四…

云原生应用里的服务发现

服务定义: 服务定义是声明给定服务如何被消费者/客户端使用的方式。在建立服务之间的同步通信通道之前,它会与消费者共享。 同步通信中的服务定义: 微服务可以将其服务定义发布到服务注册表(或由微服务所有者手动发布)…

flask--->CBV/模板/请求响应/session

CBV 1 cbv写法-1 写个类,继承MethodView-2 在类中写跟请求方式同名的方法-3 注册路由:app.add_url_rule(/home, view_funcHome.as_view(home)) #home是endpoint,就是路由别名2 cbv加装饰器-方式一:class Home(MethodView):decor…

视频添加字幕

1、依靠ffmpeg 命令 package zimu;import java.io.IOException;public class TestSrt {public static void main(String[] args) {String videoFile "/test/test1.mp4";String subtitleFile "/test/test1.SRT";String outputFile "/test/testout13…

Redis入门

0目录 1.Redis入门 2.Redis定义;特点及数据类型 3.Value为List类型 4.Value值类型为Set 5.Value值类型为Hash 6.Value值类型为Zset 1.Redis入门 Redis入门 解压包,运行redis-server.exe 安装可视化软件测试链接 命名测试链接 点击确定 2.Redis…

Python模块—Requests模块

文章目录 Requests库1.介绍2.requests 发送请求3.Response查看响应 Requests库 1.介绍 Requests库:python中的“浏览器”,基于urllib的HTTP库。 安装:pip install requests 操作步骤: 导包 发送接口请求 查看响应数据 2.r…

基于ArcGIS污染物浓度及风险的时空分布

在GIS发展的早期,专业人士主要关注于数据编辑或者集中于应用工程,以及主要把精力花费在创建GIS数据库并构造地理信息和知识。慢慢的,GIS的专业人士开始在大量的GIS应用中使用这些知识信息库。用户应用功能全面的GIS工作站来编辑地理数据集&am…

ResNet50卷积神经网络输出数据形参分析-笔记

ResNet50卷积神经网络输出数据形参分析-笔记 ResNet50包含多个模块,其中第2到第5个模块分别包含3、4、6、3个残差块 5049个卷积(3463)*31和一个全连接层 分析结果为: 输入数据形状:[10, 3, 224, 224] 最后输出结果:linear_0 [10,…

git 版本回退

git 没有push之前,可以用git reset --mixed回退,就是把add 的内容和commit的内容都撤销 在push之后,你只有2种操作 1.git reset 退回到你想要的那个版本 有配置选项 如果是soft就是当前版本删掉,之前改的代码保留,ha…

TikTok海外抖音云控抢金币宝箱

TikTok海外抖音云控抢金币宝箱 中芯密科云控系统是一个稳定、操作简单的自动化管理工具,专为大型机房设计,可以监控、控制和管理机房内的设备。该系统具有负载均衡、操作简单、高容错等特点,能够提高机房设备的稳定性和可用性。 该系统具有以…

java使用openOffice将excel转换pdf时,将所有列显示在一页

1.接上文,格式转换的基础问题已解决,但还有些细节问题需要单独处理,如excel转换至pdf时,如何将所有列显示在一页的问题,此问题大家都有遇到,解决方案也比较多,我也尝试过重写某类,来…

Java基础面试题1

Java基础面试题 一、面向对象和集合专题 1. 面向对象和面向过程的区别 面向过程:是分析解决问题的步骤,然后用函数把这些步骤一步一步地实现,然后在使用的时候一一调用则可。性能较高,所以单片机、嵌入式开发等一般采用面向过程…

OPENCV C++(三)二值化灰度函数+调用摄像头+鼠标响应+肤色检测

RGB转灰度函数 cvtColor(image, gray, COLOR_BGR2GRAY); 图像 目标图像 rgb转灰度 大津法二值化函数 threshold(gray, result1, 84, 255, THRESH_OTSU); 灰度图,目标图,阈值,大于阈值的转换的像素值,方法为大津法 自适应二值…

Stable diffusion 三大基础脚本 提示词矩阵,载入提示词,XYZ图表讲解

目录 0.本章讲解 1.提示词矩阵(prompt matrix) 1.2.提示词矩阵功能选项 1.2.1.把可变部分放在提示词文本的开头 1.2.2.为每张图片使用不同随机种子 1.2.3.选择提示词 1.2.4.选择分割符 1.2.5.宫格图边框(像素) 2.从文本框或文件载入提示词(Pro…

【Android ndk内存泄露检测】

1、 google支持方式 (88条消息) Android native memory leak detect (Android native内存泄露检测)_良秋的专栏-CSDN博客_android native 内存泄露 封装 shell 脚本 | Android NDK | Android Developers (google.cn) GitHub - wangwangchen/malloc-debug: study of mall…

获取k8s scale资源对象的命令

kubectl get --raw /apis/<apiGroup>/<apiVersion>/namespaces/<namespaceName>/<resourceKind>/<resourceName>/scale 说明&#xff1a;scale资源对象用来水平扩展k8s资源对象的副本数&#xff0c;它是作为一种k8s资源对象的子资源存在&#xf…

STM32F103——基础篇

目录 1、寄存器基础知识 2、STM32F103系统架构 2.1 Cortex M3 内核&芯片 2.2 STM32F103系统架构 3、存储器映射 4、寄存器映射 4.1 寄存器描述解读 4.2 寄存器映射举例 4.3 寄存器地址计算 4.4 stm32f103xe.h 寄存器映射 1、寄存器基础知识 概念&#xff1a;寄存…

018-从零搭建微服务-系统服务(五)

写在最前 如果这个项目让你有所收获&#xff0c;记得 Star 关注哦&#xff0c;这对我是非常不错的鼓励与支持。 源码地址&#xff08;后端&#xff09;&#xff1a;https://gitee.com/csps/mingyue 源码地址&#xff08;前端&#xff09;&#xff1a;https://gitee.com/csps…

谈谈对Android音视频开发的探究

在日常生活中&#xff0c;视频类应用占据了我们越来越多的时间&#xff0c;各大公司也纷纷杀入这个战场&#xff0c;不管是抖音、快手等短视频类型&#xff0c;虎牙、斗鱼等直播类型&#xff0c;腾讯视频、爱奇艺、优酷等长视频类型&#xff0c;还是Vue、美拍等视频编辑美颜类型…

局域网部署,用WorkPlus视频会议保密又安全

用户采用私有化部署视频会议软件的情况主要有以下几种因素&#xff1a; 1. 针对机密性高的会议&#xff1a;如果有涉及高度机密的商业谈判或敏感信息交流等重要会议&#xff0c;政府、军工、企业等用户会选择局域网内部署视频会议软件&#xff0c;以保证信息安全。 2. 频繁进…