设计模式(主要的五种)

1.设计模式:

设计模式就是代码设计经验

2.设计模式的类型:

分为三大类:创建型模式,结构型模式,行为模式

创建型模式:

单例模式:某个类只能有一个实例,提供一个全局的访问点。

工厂模式:一个工厂类根据传入的参数决定创建出那一种产品类的实例。

抽象工厂:创建相关或依赖对象的家族,而无需明确指定具体类。

建造者模式:封装一个复杂对象的构建过程,并可以按步骤构造。

原型模式:通过复制现有的实例来创建新的实例。

结构型模式

适配器模式:将一个类的方法接口转换成客户希望的另外一个接口。

组合模式:将对象组合成树形结构以表示“”部分-整体“”的层次结构。

装饰模式:动态的给对象添加新的功能。

代理模式:为其他对象提供一个代理以便控制这个对象的访问。

亨元模式:通过共享技术来有效的支持大量细粒度的对象。

外观模式:对外提供一个统一的方法,来访问子系统中的一群接口。

桥接模式:将抽象部分和它的实现部分分离,使它们都可以独立的变化。

行为型模式

模板模式:定义一个算法结构,而将一些步骤延迟到子类实现。

解释器模式:给定一个语言,定义它的文法的一种表示,并定义一个解释器。

策略模式:定义一系列算法,把他们封装起来,并且使它们可以相互替换。

状态模式:允许一个对象在其对象内部状态改变时改变它的行为。

观察者模式:对象间的一对多的依赖关系。

备忘录模式:在不破坏封装的前提下,保持对象的内部状态。

中介者模式:用一个中介对象来封装一系列的对象交互。

命令模式:将命令请求封装为一个对象,使得可以用不同的请求来进行参数化。访问者模式:在不改变数据结构的前提下,增加作用于一组对象元素的新功能。

责任链模式:将请求的发送者和接收者解耦,使的多个对象都有处理这个请求的机会。

迭代器模式:一种遍历访问聚合对象中各个元素的方法,不暴露该对象的内部结构。

3.单例模式:

1.一个类只有一个实例

2.只提供一个全局访问点

3.自我实例化( 一个对象在其自身的定义中创建自己的实例 )

懒汉模式在第一次调用时才创建实例,适合节省资源,但需要考虑线程安全问题。

饿汉模式在类加载时就创建实例,确保线程安全,但会占用更多资源,可能在不需要时也会初始化。

饿汉模式1:

很形象,通过getxxx静态方法把静态对象返回出去

这里的对象是私有的,防止外头的人修改,起到保护的作用

返回对象

public class UserMassage {
    //这是饿汉模式1

    //创建静态对象,自我实例化
    public static final UserMassage usermassage = new UserMassage();

    //提供全局访问点
    public  static UserMassage getUsermassage(){
        return  usermassage;
    }
    public void show(){
        System.out.println("我是单例模式");
    }

}

饿汉模式2:
public class UserMassage2 {
    //饿汉模式2
    public static final UserMassage2  usermassage;
    static {
        usermassage =  new UserMassage2();
    }
    public void show(){
        System.out.println("我是单例模式");
    }
}

懒汉模式:

先把静态对象设为null

判断静态对象是否为null

为null则生产一个返回

不为null则用这个对象

public class LayManModel {
    //懒汉模式

    //私有静态变量保存实例
    private static LayManModel layManModel;


    //提供公共的获取实例的方法
    public static LayManModel getInstance() {
        //使用synch保证线程安全
        if (layManModel == null) {
            synchronized (LayManModel.class) {
                if (layManModel == null) {
                    layManModel = new LayManModel();
                }
            }
        }

        return layManModel;
    }
        public void show () {
            System.out.println("我是懒汉模式");
        }

}

测试代码:

1.== 用来判断地址从而判断是否是同一个对象

2.通过全局访问点来创建对象

public class Main2 {
    public static void main(String[] args) {
        LayManModel layManModel1 = LayManModel.getLayManModel();
        LayManModel layManModel2 = LayManModel.getLayManModel();
        System.out.println(layManModel1 == layManModel2);
        layManModel1.show();
    }
}

优点:

在内存中只有一个实例,避免频繁的创建和销毁实例

缺点:

没有接口,不能继承

注意事项:getUserMassage() 方法中需要使用同步锁 synchronized (UserMassage.class) 防止多线程

同时进入造成 UserMassage被多次实例化

4.工厂模式:

优点

1、一个调用者想创建一个对象,只要知道其名称就可以了。

2、扩展性高,如果想增加一个产品,只要扩展一个工厂类就可以。

3、屏蔽产品的具体实现,调用者只关心产品的接口。

缺点

每次增加一个产品时,都需要增加一个具体类和对象实现工厂,使得系统中类的个数成倍增加,在一定

程度上增加了系统的复杂度,同时也增加了系统具体类的依赖。这并不是什么好事 。

面条接口:
public interface MianTiao {
    //面条抽象类
    public abstract void des();


}
三种产品:三种面条

拉面:

public class LaMian implements MianTiao{
    @Override
    public void des() {
        System.out.println("我是拉面,兰州的拉面");
    }
}

泡面:

public class PaoMian implements MianTiao{
    @Override
    public void des() {
        System.out.println("我是泡面,大家都不爱吃的泡面");
    }
}

烩面:

public class HuiMian implements MianTiao{
    @Override
    public void des() {
        System.out.println("我是烩面,河南人爱吃的烩面");
    }
}

测试方法:
public class Main {
    //传入我要生产面
    public static void main(String[] args) {
        MianTiao miantiao = SimpleNoodlesFactory.createNoodles(LA_MIAN);
        miantiao.des();
    }
}

工厂:
public class SimpleNoodlesFactory {
   
    //简单面条工厂
    protected static final int PAO_MIAN = 1;
    protected static final int LA_MIAN = 2;

    protected static final int HUI_MIAN = 3;
    //这个方法是关键,用来生产的
    public static MianTiao createNoodles(int type) {
        switch (type) {
            case PAO_MIAN:
                return new PaoMian();
            case LA_MIAN:
                return  new LaMian();

            default:
                return new HuiMian();
        }
    }
}

抽象工厂:

因为工厂和工厂不一样,这个是面条工厂,我们随着企业的扩大需要包子工厂,生产工厂的工厂就是抽象工厂,也叫二级工厂。

5.装饰模式:

装饰模式是用来替代继承的一种设计模式。它通过一种无须定义子类的方式来给对象动态增加职责,使

用对象之间的关联关系取代类之间的继承关系。降低了系统的耦合,可以动态的增加或者删除对象的职 责

接口:

public interface Showable {
    //展示接口
    public abstract void show();
}

装饰器:

public abstract class Decorator implements Showable{
    Showable showable ;//持有一个善于展示自己某个家伙
    //抽象装饰器

    //构造函数
    public  Decorator(Showable showable){
        this.showable = showable;
    }
    //无需实现因为现在装饰器还不知道如何修饰
    public abstract  void show();
}

装饰对象:

public class Girl implements Showable{
    @Override
    public void show() {
        System.out.print("女友的素颜");
    }
}

装饰功能:

描眉:

public class MiaoMei extends Decorator{

    public MiaoMei(Showable showable) {
        super(showable);
    }

    //重写接口化妆后展示 描眉
    @Override
    public void show() {
        System.out.print("描眉(");
        showable.show();
        System.out.print(")");
    }
}

涂口红:

public class TuKouHong extends Decorator{
    public TuKouHong(Showable showable) {
        super(showable);
    }

    @Override
    public void show() {
        System.out.print("涂口红(");
        showable.show();
        System.out.print(")");

    }
}

测试方法:

这个装饰模式就是套的方式

和I/O流中的创建可像

public class Main {
    public static void main(String[] args) {
        //创建女友对象
        Girl girl = new Girl();
        //将女友放入描眉类
        MiaoMei lyw = new MiaoMei(girl);
        TuKouHong cmy = new TuKouHong(lyw);
        cmy.show();
    }
}

6.代理模式:

代理模式 指由一个代理主题来操作真实主题,真实主题执行具体的业务操作,而代理主题负责其他相关 业务的处理。

/*
* 定义Network接口
*/
public interface Network {
public void browse(); // 定义浏览的抽象方法
}
/*
* 真实的上网操作
*/
public class Real implements Network {
//重写抽象方法
public void browse() {
System.out.println("上网浏览信息!");
}
}
/*
* 代理上网
*/
public class Proxy implements Network {
private Network network;
// 设置代理的真实操作
public Proxy(Network network) {
this.network = network; // 设置代理的子类
}
// 身份验证操作 其他操作
public void check() {
System.out.println("检查用户是否合法!");
}
//代码实现上网
public void browse() {
this.check(); // 调用具体的代理业务操作
this.network.browse(); // 调用真实的上网操作
}
}
public static void main(String args[]) {
Network net = null; // 定义接口对象
net = new Proxy(new Real()); // 实例化代理,同时传入代理的真实操作
net.browse(); // 调用代理的上网操作
}

7.观察者模式

就是举个例子:订报纸

报纸厂家和订阅报纸的人之间这种一对多的就可以称为观察者模式

报纸厂家是被观察者

订阅报纸的人是观察者

当你订阅了 一份报纸,每天都会有一份最新的报纸送到你手上,有多少人订阅报纸,报社就会发多少份报纸,报社 和订报纸的客户就是上面文章开头所说的“一对多”的依赖关系

奶厂:

接口:

public interface Subject {
  

    //订阅
    void attach(Observer observer);
    //取消订阅
    void detach(Observer observer);
    //通知变动
    void  notifyChanged();

}

实例:

public class RealSubject implements Subject{
    //奶厂

    //本奶厂下订奶的人集合
    private List<Observer> observerList = new ArrayList<Observer>();
    //添加订阅者
    @Override

    public void attach(Observer observer) {
        observerList.add(observer);
    }
    //删除订阅者
    @Override
    public void detach(Observer observer) {
        observerList.remove(observer);
    }
    //消息通知订阅者
    @Override
    public void notifyChanged() {
        for (Observer observer : observerList) {
            observer.update();
        }
    }



}

订牛奶的:

接口:

package ObserverTest;

public interface Observer {

    /**
     * 接收变动通知
     */
    void update();
}

实例:

package ObserverTest;

public class RealObject implements Observer{
    //奶厂
    @Override
    public void update() {
        System.out.println("通知");
    }
}

测试方法:
public class mainTest {
    public static void main(String[] args) {

        Subject subject = new RealSubject(); //创建奶厂
        Observer observer = new RealObject();//创建订阅人
        subject.attach(observer);//订阅人订阅 subject奶厂
        subject.notifyChanged();//奶厂发布消息 订阅者接收
    }
}

奶厂可以管理订牛奶的,删除,添加或者发布消息

订牛奶的只能接收消息

总结:

通过定义一个抽象接口 Subject(奶厂),我们可以将 奶厂 和 订奶的人 的行为统一起来。

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

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

相关文章

Wireshark中的length栏位

注&#xff1a;Ethernet II的最小data length为46&#xff0c;如果小于&#xff0c;会补全到46. 1.指定网卡抓取的&#xff0c;链路为ethernet。 IPv4 Ethernet II 长度为 14 bytes - L1ipv4 header中的length包括header和payload的总长度 - L2wireshark中length表示抓取的pac…

Java线程池浅谈(创建线程池及线程池任务处理)

1-认识线程池 什么是线程池&#xff1f; 线程池就是一个可以复用线程的技术。 不使用线程池的问题 比方说淘宝&#xff0c;不使用线程池&#xff0c;现在有一亿个线程同时进来&#xff0c;CPU就爆了。用户每发起一个请求&#xff0c;后台就需要创建一个新线程来处理&#xf…

缓冲区溢出,数据被踩的案例学习

继续在ubuntu上学习GDB&#xff0c;今天要学习的是缓冲区溢出。 程序的地址&#xff1a; GitHub - gedulab/gebypass: bypass password by heap buffer overflow 编译的方法&#xff1a; gcc -g -O2 -o gebypass gebypass.c 照例设置一下科学shangwang代理&#xff1a; e…

GoogleCloud服务器的SSH连接配置

首先&#xff0c;Google的服务器默认是通过自带的SSH网页端连接的&#xff0c;比较麻烦和容易断开&#xff0c;不是很好用&#xff0c;常见的解决办法有两种一种是通过修改ssh的配置&#xff0c;添加密码的方式进行连接&#xff0c;一种是通过配置公钥进行连接。 密码连接之前有…

万字长文解读深度学习——ViT、ViLT、DiT

文章目录 &#x1f33a;深度学习面试八股汇总&#x1f33a;ViT1. ViT的基本概念2. ViT的结构与工作流程1. 图像分块&#xff08;Image Patch Tokenization&#xff09;2. 位置编码&#xff08;Positional Encoding&#xff09;3. Transformer 编码器&#xff08;Transformer En…

MQ集群

目录 MQ集群 集群分类 普通集群 集群结构和特征 集群的部署 获取cookie 准备集群配置 启动集群 镜像模式 镜像模式的特征 镜像模式的配置 exactly模式 仲裁队列 集群特征仲裁队列&#xff1a;仲裁队列是3.8版本以后才有的新功能&#xff0c;用来替代镜像队列&#…

零基础Java第十七期:内部类

目录 一、Object类 1.1. 获取对象信息 1.2. 对象比较equals方法 1.3. hashCode方法 ​编辑 二、内部类 一、Object类 1.1. 获取对象信息 Object是Java默认提供的一个类。Java里面除了Object类&#xff0c;所有的类都是存在继承关系的。默认会继承Object父 类。即所有…

Docker 篇-Docker 详细安装、了解和使用 Docker 核心功能(数据卷、自定义镜像 Dockerfile、网络)

&#x1f525;博客主页&#xff1a; 【小扳_-CSDN博客】 ❤感谢大家点赞&#x1f44d;收藏⭐评论✍ 文章目录 1.0 Docker 概述 1.1 Docker 主要组成部分 1.2 Docker 安装 2.0 Docker 常见命令 2.1 常见的命令介绍 2.2 常见的命令演示 3.0 数据卷 3.1 数据卷常见的命令 3.2 常见…

GitCode光引计划有奖征文大赛

一、活动介绍 GitCode平台汇聚了众多杰出的G-Star项目&#xff0c;它们犹如璀璨星辰&#xff0c;用各自的故事和成就&#xff0c;为后来者照亮前行的道路。我们诚邀广大开发者、项目维护者及爱好者&#xff0c;共同撰写并分享项目在GitCode平台上托管的体验&#xff0c;挖掘平…

什么是CRM系统?

越来越多的企业意识到&#xff1a;如何有效管理与客户的关系、提升客户满意度&#xff0c;并通过这些提升推动销售增长&#xff0c;已经成为许多公司亟待解决的问题。为此&#xff0c;客户关系管理&#xff08;Customer Relationship Management&#xff0c;简称CRM&#xff09…

ctfshow DSBCTF web部分wp

ctfshow 单身杯 web部分wp web 签到好玩的PHP 源码&#xff1a; <?php error_reporting(0); highlight_file(__FILE__);class ctfshow {private $d ;private $s ;private $b ;private $ctf ;public function __destruct() {$this->d (string)$this->d;$this…

不一样的CSS(一)

目录 前言&#xff1a; 一、规则图形 1.介绍&#xff1a; 2.正方形与长方形&#xff08;实心与空心&#xff09; 2.1正方形&#xff1a; 2.2长方形 3.圆形与椭圆形&#xff08;空心与实心&#xff09; 3.1圆形与椭圆形 4.不同方向的三角形 4.1原理 4.2边框属性 5.四…

VUE实现点击导航栏进行切换右边内容

首先看看效果&#xff0c;左边导航栏进行切换&#xff0c;右边内容进行切换 代码如下 <div><el-tabs :tab-position"tabPosition" style"height: 800px;"><el-tab-pane label"通知通告">通知通告</el-tab-pane><el-t…

微信小程序——实现二维码扫描功能(含代码)

✅作者简介&#xff1a;2022年博客新星 第八。热爱国学的Java后端开发者&#xff0c;修心和技术同步精进。 &#x1f34e;个人主页&#xff1a;Java Fans的博客 &#x1f34a;个人信条&#xff1a;不迁怒&#xff0c;不贰过。小知识&#xff0c;大智慧。 &#x1f49e;当前专栏…

OpenGL ES 文字渲染进阶--渲染中文字体

旧文 OpenGL ES 文字渲染方式有几种? 一文中分别介绍了 OpenGL 利用 Canvas 和 FreeType 绘制文字的方法。 无论采用哪种方式进行渲染,本质上原理都是纹理贴图:将带有文字的图像上传到纹理,然后进行贴图。 渲染中文字体 利用 Canvas 绘制中文字体和绘制其他字体在操作方式上…

redis实现消息队列的几种方式

一、了解 众所周知&#xff0c;redis是我们日常开发过程中使用最多的非关系型数据库&#xff0c;也是消息中间件。实际上除了常用的rabbitmq、rocketmq、kafka消息队列&#xff08;大家自己下去研究吧~模式都是通用的&#xff09;&#xff0c;我们也能使用redis实现消息队列。…

WLAN消失或者已连接但是访问不了互联网

目录 1、WLAN已连接但是访问不了互联网 2、WLAN图标消失 今晚电脑突然连不上网了&#xff0c;重启试了好多种办法都没有用。 1、WLAN已连接但是访问不了互联网 这个的问题很多&#xff0c;建议直接网络重置&#xff0c;即将网络驱动全部删除&#xff0c;然后重新安装。 首先…

Hadoop生态圈框架部署(六)- HBase完全分布式部署

文章目录 前言一、Hbase完全分布式部署&#xff08;手动部署&#xff09;1. 下载Hbase2. 上传安装包3. 解压HBase安装包4. 配置HBase配置文件4.1 修改hbase-env.sh配置文件4.2 修改hbase-site.xml配置文件4.3 修改regionservers配置文件4.4 删除hbase中slf4j-reload4j-1.7.33.j…

【微服务】Docker 容器化

一、初识Docker 1. 为什么需要 Docker 大型项目组件较多&#xff0c;运行环境也较为复杂&#xff0c;部署时会遇到一些问题&#xff1a; 依赖关系复杂&#xff0c;容易出现兼容性的问题开发、测试、生产环境有差异 Docker 如何解决依赖的兼容问题 将应用的Libs&#xff08;…

「Py」Python基础篇 之 Python都可以做哪些自动化?

✨博客主页何曾参静谧的博客&#x1f4cc;文章专栏「Py」Python程序设计&#x1f4da;全部专栏「Win」Windows程序设计「IDE」集成开发环境「UG/NX」BlockUI集合「C/C」C/C程序设计「DSA」数据结构与算法「UG/NX」NX二次开发「QT」QT5程序设计「File」数据文件格式「UG/NX」NX定…