创建型模式---【JAVA&JS】

  • 创建型模式关注对象的创建过程
  • 将对象的创建和使用分离(组件封装)

工具类

config.xml

<?xml version="1.0"?>
<config>
	<chartType>histogram<chartType>
</config>

XMLUtil

public class XMLUtil {
  public static Object getBean() {
    try {
      DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
      DocumentBuilder builder = documentBuilderFactory.newDocumentBuilder();
      Document doc;
      doc = builder.parse(new File("src//firstexp//config.xml"));

      NodeList nl = doc.getElementsByTagName("className");
      Node classNode = nl.item(0).getFirstChild();
      String cName = classNode.getNodeValue();

      Class c = Class.forName(cName);
      Object obj = c.newInstance();
      return obj;

    }
    catch (Exception e){
      e.printStackTrace();
      return null;
    }
  }
}


// 使用
IAutoFactory factory;
    factory = (IAutoFactory) XMLUtil.getBean();
    factory.createMed().ignition();
    factory.createMed().startup();

简单工厂模式

概述

  • 通俗版
    一套图标库里有不同类型的图表,根据不同的参数获得不同的类型的图表
  • 标准版
    • 定义一个工厂类,它可以根据参数的不同返回不同类的实例,被创建的实例通常都具有共同的父类
    • 类创建型模式,静态工厂方法

结构

  • Factory(工厂角色):工厂类,;提供了静态方法factoryMethod(),返回类型为抽象产品类型Product
  • Product(产品角色): 父类,图表库
  • ConcreteProduct(具体产品角色):不同类型的图表
  • 结构图

模板

步骤1:抽象产品类
抽象产品类有以下几个重点:

  • 产品类重构,根据实际情况设计一个产品层次结构
  • 将所有公共代码 =>抽象产品类
  • 声明一些抽象方法,共不同的具体产品实现
public abstract class Product {
  // 所有产品类的公共业务方法
  public void methodSame() {
  
  }
 
  // 声明抽象业务方法
  public abstract void methodDiff();
}

步骤2:在具体产品类中实现抽象产品类中声明的抽象业务方法

public class ProductA extends Product {
  // 实现业务方法
  public void methodDiff(){
   
  }
 
} 

** 步骤3:简单工厂实现**

public class SimpleFactory {
  public static Product getProduct(String arg) {
    Product product = null;
    if (arg.equalsIgnoreCase("A")){
      product = new ProductA();
      // 初始化设置A
    }
    else if (arg.equalsIgnoreCase("B")){
      product = new ProductB();
      // 初始化设置B
    }
    return product
  }
  
}

** 步骤4:具体使用**

main() {
	Product product;
	product = Factory.getProduct("A");
	product.methodSame();
	product.methodDiff();
}

优缺点

优点:

  • 客户无需知道所创建的具体产品类的类名,只需要知道对应的参数
  • 通过引入配置文件,可以在不修改任何客户端的代码情况下,更换和新增具体产品类

缺点:

  • 由于工厂集中了所有产品的创建逻辑,一旦失效,则系统瘫痪
  • 增加系统中类的个数且增加了系统的复杂度和理解读
  • 系统扩展困难

适用环境:

  • 负责创建的对象较少
  • 客户端只知道传入工厂类的参数。

工厂方法模式

工厂方法模式解决了,简单工厂模式中 新增具体产品时需要改动工厂方法的缺点。
其解决方法为:不再提供一个统一工厂去创建所有产品,而是给不同产品建立各自的工厂

结构

  • Product(抽象产品):它是定义产品的接口,是工厂方法模式所创建对象的父类
  • ConcreteProduct(具体产品):它实现了抽象产品接口,某种类型的具体产品由专门的具体工厂创建,具体工厂和具体产品直接一一对应
  • Factory(抽象工厂)
  • ConcreteFactory(具体工厂)

模板

步骤1:建立产品类
同简单工厂
步骤2:建立抽象工厂类

public interface Factory {
	public Product factoryMethod();
}

步骤3:具体工厂

public class ConcreteFactory implements Factory{
	public Product factoryMethod(){
		return new ContreteProduct();
	}
}

步骤四:客户端

Factory factory;
facotry = new ContreteFactory();
Product  product;
product = factory.factoryMethod();

实例

系统日志记录:有文件和数据两种形式

实例结构图

代码步骤
若需要增加并使用新的日志记录器,只需要对应增加一个新的具体工厂,然后再客户端代码中修改具体工厂的类名。

步骤1:Logger:日志记录器接口,充当抽象产品角色

public interface Logger {
	public void writeLog();
}

步骤2:DatabaseLogger/FileLogger: 数据库/文件日志记录器,充当具体产品角色

public class DatabaseLogger implements Logger {
	public void writeLog(){
		System.out.println("数据库日志记录")
	}
}

步骤3: LoggerFactory: 日志记录器工程接口,充当抽象工厂角色

public interface LoggerFactory() {
	public Logger createLogger(); // 抽象工厂方法
}

步骤4: DatabaseLoggerFactory: 数据库/文件日志记录器工厂类,充当具体工厂角色

public class DatabaseLoggerFactory implements LoggerFactory {
	public Logger createLogger () {
		// 连接数据库,代码省略
		// 创建数据库日志记录器对象
		Logger logger = new DatabaseLogger();
		return logger;
	}
}

步骤5: 客户端测试

public Class client {
	public static void main(String args[]){
		LoggerFactory factory;
		Logger logger;
		factory = new FileLoggerFactory();
		logger = factory.createLogger();
		logger.writeLog()
	}
}

工厂方法的隐藏

工厂方法隐藏的结构图如图所示
LoggerFactory代码

public abstract class LoggerFactory {
	// 在工厂类中直接调用日志记录器类的业务方法writeLog()
	public void writeLog(){
		Logger logger = this.createLogger();
		logger.writeLog();	
	}
	public abstract Logger createLogger();
	
}

// 客户端
LoggerFactory factory;
factory = (LoggerFactory) XMLUtil.getBean()
factory.writeLog()

抽象工厂

工厂方法中每个具体工厂只有一个产品,可能会导致系统中存在大量工厂
抽象工厂将一类产品形成一个产品族不同工厂即为不同等级

结构

  • 抽象工厂:声明了一组用于创建一族产品的方法,每个方法对应一种产品
  • 具体工厂:实现了在抽象工厂中声明的创建产品的方法
  • 抽象产品:为每种产品提供接口
  • 具体产品

模板

步骤1:抽象工厂

public interface AbstractFactory{
	public AbstractProductA createProductA();
	public AbstractProductB createProductB();
}

步骤2: 具体工厂

public class ConCreteFactory extends AbstractFactory {
	// 工厂方法一
	public AbstractproductA createProductA(){
		return new ConcreteProductA();
	}
}

实例

两种不同的应用主题,每种主题主要更改按钮、文本框、组合框的样式
结构图如下

具体步骤:
步骤1: Button/Text/Field接口,只举一个

public interface Button {
	public void display();
}

步骤2: Spring/SummerButton,两种不同的分隔,也是只举例一个

public class SpringButton implements Button {
	public void display(){....}
}
public class SummerButton implements Button {
	public void display(){....}
}

步骤3: 抽象工厂

public interface SkinFactory {
	public Button createButton();
	public Text createText();
	...
}

步骤4: 具体工厂

public SpringSkinFactory implements SkinFactory {
	public Button createButton(){
		return new SpringButton();
	};
	public Text createText(){....};
	...
}

建造者模式

将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示
建造者模式是一种对象创建型模式,它将客户端与包含多个部件的复杂对象的创建过程分离,客户端无须知道复杂对象的内部组成与装配形式,只需要知道所需建造者的类型即可。

结构图

  • Builder(抽象建造者) 在该接口中一般声明两类方法,一类是buildPartX(),用于创建复杂对象的各个部件;另一类是getResult(),用于返回复杂对象。既可以是接口,也可以是类
  • ConcreteBuilder(具体建造者):它实现了Builder接口,实现各个部件的具体构造和装配方法,定义并明确所创建的复杂对象,还可以提供一个方法返回创建好的复杂产品对象
  • Product(产品): 它是被构建的对象,包含多个组成部件,具体建造者创建改产品的内部表示并定义它的装配过程
  • **dIrector(指挥者):**指挥者又称导演类,负责安排复杂对象的构建次序。

客户端一般只与指挥者进行交互,在客户端确定具体建造者的类型,并实例化具体建造者对象,然后通过指挥者类的构造函数或者Setter方法将该对象传入指挥者类中

模板

一个典型的复杂对象类的示例代码如下:

public class Product {
	private String partA;// 定义部件,可以是任意类型
	private String partB;
	// partAde Getter和Setter方法
}

在抽象建造者类中定义了产品的创建方法和返回方法。
在抽象类Builder中声明了一系列buildPartX()方法,用于创建复杂产品的各个部件,具体建造过程在ConcreteBuilder中实现。

public abstract class Builder {
	// 创建产品对象
	protected Product product = new Product();
	//部件
	public abstract void buildPartA();
	//返回产品对象
	public Product getResult(){
		return product;
	}
}

在ConcreteBuilder中实现了这些buildPartX()方法,通过调用Product的setPartX()方法,可以给产品对象成员赋值

public class ConcreteBuilder extends Builder {
	public void buildPartA(){
		product.setPartA("A")
	}
	.....
}

Director类,用于控制产品的创建过程
指挥者类中可以注入一个抽象建造者类型的对象,它提供了一个建造方法construct(),在该方法中调用了builder对象的构造部件的方法,最后返回一个产品对象

public class Director {
	private Builder builder;

	public Director(Builder builder) {
		this.builder = builder
	}
	
	public void setBuilder(Builder builder) {
		this.builder = builder;
	}
	
	// 产品构建与组装方法
	public Product construct() {
		builder.builderPartA();
		return builder.getResult();
	}
}

客户端代码

Builder builder = new ConcreteBuilder();
Director director = new Director(builder);
Product product = director.construct();

建造者模式与抽象工厂模式的区别与共同点
建造者模式返回一个完成的复杂产品
抽象工厂模式返回一系列相关的产品
抽象模式中,客户端通过选择具体的工厂来生成所需对象
建造者模式中,客户端通过指定具体建造者类型来指导Director类如何去生成对象,侧重于一步步构造一个复杂对象

实例:游戏角色类

构造图
代码仓库

适用环境

  • 需要生成的产品对象有复杂的内部结构
    • 这些产品对象通常包含多个成员变量
  • 需要生成的产品对象的属性相互依赖
    • 需要指定其生成顺序
  • 对象的创建过程独立于创建该对象的类
    • 在建造者模式中通过引入指挥者类将创建过程封装在指挥者类中,而不是在建造者类和客户类中
  • 隔离复杂对象的创建和使用
    • 使得相同的创建过程可以创建不同的产品

原型模式

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

结构

结构图

  • Prototype(抽象原型类):它是声明克隆方法的接口,是所有具体原型类的公共父类
  • ConcretePrototype(具体原型类):它实现在抽象原型类中声明的克隆方法,在方法中返回自己的一个克隆对象
  • Client类

浅克隆
引用类型只复制地址
深克隆
全部复制一遍

实例

结构图
代码

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值