zoukankan      html  css  js  c++  java
  • 创建型设计模式小结

    概述

      创建型模式,就是用来创建对象的模式,它抽象了对象的创建过程。本系列文章介绍了Gof设计模式中的5种创建型模式,另外对简单工厂模式也进行了介绍,下面通过一个表格来说明它们之间的关系。

    名称

    GoF的定义

    功能描述

    Singleton

    保证一个类仅有一个实例,并提供一个该实例的全局访问点。

    解决的是类实例化个数的问题,严格控制实体对象的数量

    Simple Factory

    非23种Gof模式,没有Gof定义(个人定义:专门定义一个类来负责创建其他类的实例,被创建的实例常常具有共同的父类。)

    解决的是“某个对象”的创建工作,由于需求的变化,这个对象的具体实现常常面临着剧烈的变化,但是这个对象拥有的接口相对稳定。简单工厂实现了客户端和对象创建的解耦。

    Factory Method

    定义创建对象的接口,让子类决定实例化哪一个类。工厂方法使得一个类的实例化延迟到其子类。

    功能和简单工厂一样,它具有简单工厂的优点,并规避了简单工厂的缺点(违反“开放-关闭原则”)

    Abstract Factory

    提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类。

    抽象工厂解决了一个系列易变对象的创建问题

    Builder

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

    应对项目中一些复杂对象的创建工作。所谓“复杂对象”,是指对象中还含有其它的子对象。

    Prototype

    使用原型实例指定创建对象的种类,并通过复制这个原型创建新的对象

    解决了某些结构复杂的对象的创建工作。由于需求的变化,这些对象经常面临着剧烈的变化,但是它们却拥有比较稳定一致的接口,原型模式通过原型(可以理解为一个特殊的工厂类)来克隆易变对象

    为什么需要创建型模式

      所有的创建型模式都有两个永恒的主题:第一,它们都将系统使用哪些具体类的信息封装起来;第二,它们隐藏了这些类的实例是如何被创建和组织的。外界对于这些对象只知道它们共同的接口,而不清楚其具体的实现细节。正因如此,创建型模式在创建什么(what)、由谁(who)创建、以及何时(when)创建这些方面,都为软件设计者提供了尽可能大的灵活性。下面通过应用场景来说明。

      假设现在要开发一个游戏,游戏中会用到一个现代风格房屋的对象,我们一般会使用如下代码来创建:

    ModernRoom room = [[ModernRoom alloc] init];

      这样一个现代风格的房屋对象就创建好了。但现在由于客户需求的变化,客户方要求创建一个古典风格的房屋,那么我们就需要将上面的代码修改为:

    ClassicalRoom room = [[ClassicalRoom alloc] init];

      从代码看也没什么问题,但大家可以试想一下:在我们的程序中可能有很多地方使用了这样风格的创建代码,这里仅仅是假设房屋的风格变化,就需要修改程序中所有的房屋风格创建代码,那么其他的话,大家可以想象一下修改的工作量。现在有了创建型模式,我们对对象创建过程采用工厂方法模式封装,把对象的创建放在一个工厂方法中,客户端调用的代码可能如下:

    // 这个地方的@" ModernRoomFactory "可以写到配置文件中
    id<Factory> factory = [[[NSClassFromString(@"ModernRoomFactory") alloc] init] autorelease];
    id<IRoom> chart = [factory createRoom];
    // 其他操作......

      当房屋的风格变化时,我们只需要修改配置文件中@" ModernRoomFactory ",代码不做任何改动就可以了。这就是我们为什么需要创建型模式。创建者模式作用可以概括为如下两点:

    • 封装创建逻辑,绝不仅仅是alloc一个对象那么简单。
    • 封装创建逻辑变化,客户代码尽量不修改,或尽量少修改。

    如何使用创建型模式

      我们继续上面的游戏开发场景:假定在游戏中我们需要用到墙(Wall)、屋子(Room)、门(Door)等部件。同样是对象的创建问题,但是会根据所要解决的问题不同而使用不同的创建型模式。

      假定一个屋子只允许有一个门存在,那么这就是一个使用Signleton模式的例子,确保只有一个Door类的实例被创建,解决的是对象创建个数的问题

      在游戏中需要创建墙、屋子的实例时,为了避免直接对构造器的调用而实例化类,也是应对这些类可能有不同表现的问题,这时我们会使用简单工厂模式或工厂方法模式,每一个部件都有它自己的工厂类,解决的是“单个对象”的需求变化问题

      更进一步,在游戏场景中,不可能只有一种风格的墙或屋子,可能有现代风格的(Modern)、古典风格(Classical)等其他系列风格的部件。这时就是一系列对象的创建问题了,可以使用抽象工厂模式解决的是“系列对象”的需求变化问题

      现在再考虑一下:我们知道一个屋子一般由4面墙、一扇窗户、一张门、一个天花板构成,但具体用什么风格的墙、窗户、门、天花板是不断变化的,这时我们可以用生成器模式解决的是“对象部分”的需求变化问题

      如果在游戏中,需要大量的古典风格或现代风格的墙或屋子,这时我们可以通过拷贝一个已有的原型对象来生成新对象,这就是原型模式通过克隆来解决“易变对象”的创建问题

      究竟选用哪一种模式,取决于很多的因素。使用Abstract FactoryPrototypeBuilder的设计比使用Factory Method的设计更加灵活,但是也更加复杂,尤其Abstract Factory需要庞大的工厂类来支持。通常,设计以使用Factory Method开始,当需要更大的灵活性时,设计便会向其他设计模式演化,了解多个设计模式,可以让你有更多的选择余地。

      返回目录

  • 相关阅读:
    ASP.NET CORE 使用Consul实现服务治理与健康检查(2)——源码篇
    ASP.NET CORE 使用Consul实现服务治理与健康检查(1)——概念篇
    Asp.Net Core 单元测试正确姿势
    如何通过 Docker 部署 Logstash 同步 Mysql 数据库数据到 ElasticSearch
    Asp.Net Core2.2 源码阅读系列——控制台日志源码解析
    使用VS Code 开发.NET CORE 程序指南
    .NetCore下ES查询驱动 PlainElastic .Net 升级官方驱动 Elasticsearch .Net
    重新认识 async/await 语法糖
    EF添加
    EF修改部分字段
  • 原文地址:https://www.cnblogs.com/eagle927183/p/3480059.html
Copyright © 2011-2022 走看看