Java设计模式-简单工厂模式

Posted Zip Zou

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Java设计模式-简单工厂模式相关的知识,希望对你有一定的参考价值。

简单工厂模式

模式内容

简单工厂模式又被称为静态模式,其实现简单,实现过程基本遵循如下过程:

  1. 建立产品接口;
  2. 具体化产品类;
  3. 定义简单工厂,并定义静态方法,生产所有对象。

但是严格意义来说,简单工厂模式并不算一个真正的"设计模式"。

The Simple Factory isn’t actually a Design Pattern; it’s more of a programing idiom. But it is commonly used, so we’ll give it a Head First Pattern Honorable Mention.

在Head First原书中,有上述的提及,说明简单工厂只是一种被开发人员所普遍使用的编程风格。

但是我们还是简单地介绍一下该模式,首先其类图如下:

从类图中我们可以看到,有一个产品接口,并派生了两个具体产品ProductAProductB,而工厂的职责便是负责生产这些产品,我们可以有如下的实现。

接口类:

public interface Product 
  public void doSomeThing();

产品A类:

public class ProductA implements Pruduct 
  public void doSomeThing() 
    System.out.println("A do...");
  

产品B类:

public class ProductB implements Pruduct 
  public void doSomeThing() 
    System.out.println("B do...");
  
 

工厂类:

public ProductFactory 
  public static Product produceProduct(String name) 
    if ("A".equals(name)) 
      return new ProductA();
     else if ("B".equals(name)) 
      return new ProductB();
    
  

客户端类:

public class SimpleFactoryClient 

	public static void main(String[] args) 
		Product product = ProductFactory.produceProduct("A");
		product.doSomeThing();
		product = ProductFactory.produceProduct("B");
		product.doSomeThing();
	

通过上述代码,即可使用工厂快速通过参数的不同,动态地获取到不同的产品,并使用产品的方法。

从实现中我们可以看出,对于产品类而言,其具体的创建过程交给了工厂,而客户端在获得产品时,不再需要手动地new创建对象,而时根据产品名称动态地获取到所需要的产品,因此简单工厂能够将对象的创建过程和对象的使用过程隔离

在Head First中,其使用了Pizza的例子,对简单工厂模式进行说明举例。

该例子也说明了简单工厂的具体模式,不同的是在该类图中依赖关系将其画到了SimplePizzaFactoryPizza之间,但其意义相同。

JDK中的简单工厂

public class DateFormateTest 

	public static void main(String[] args) 
		DateFormat format = DateFormat.getDateTimeInstance(DateFormat.FULL, DateFormat.SHORT);
		String now = format.format(new Date());
		System.out.println(now);
	
	

通过使用DateFormat format = DateFormat.getDateTimeInstance(DateFormat.FULL, DateFormat.SHORT);可以快速获得一个DateFormat对象,而只需要提供DateStyleTimeStyle,这便是一个简单工厂模式的应用,在JDK中,DateFormat为一个抽象类,而其子类有SimpleDateFormat类,但通过使用简单工厂,仅需要指定style即可获得格式化类,客户端无需关心具体的格式化类是什么。

不仅如此,在JDK加密算法的实现中,也使用了简单工厂。

public class CipherTest 

	public static void main(String[] args) 
		try 
			KeyGenerator aes = KeyGenerator.getInstance("AES");
			SecretKey secKey = aes.generateKey();
			Cipher cipher = Cipher.getInstance("AES");
			cipher.init(Cipher.ENCRYPT_MODE, secKey);
			byte[] encoded = cipher.doFinal("Hello World".getBytes("utf-8"));
			System.out.println(new String(encoded, "utf-8"));
		 catch (NoSuchAlgorithmException e) 
			e.printStackTrace();
		 catch (NoSuchPaddingException e) 
			e.printStackTrace();
		 catch (InvalidKeyException e) 
			e.printStackTrace();
		 catch (IllegalBlockSizeException e) 
			e.printStackTrace();
		 catch (BadPaddingException e) 
			e.printStackTrace();
		 catch (UnsupportedEncodingException e) 
			e.printStackTrace();
		
	

适用场景

  • 工厂类需要负责的产品类有限,且产品的数量变化不大;
  • 客户端不清楚所需对象的细节,只知道对象的具体名称和使用方式。

优缺点

优点:

  • 使用简单工厂可以将产品的创建过程和使用过程隔离,使得使用者无需关注产品的内部结构和创建细节;
  • 结合使用配置文件,可以在不修改代码的情况下,动态地修改系统中使用的类(这对于框架设计来说是一个很重要的方式,配置文件为使用者提供了替换和选择相关组件的能力);
  • 将客户端与各个产品解耦,减少类的依赖。

缺点:

  • 在工厂类会创建所有产品,当产品增加时,工厂类方法内部需要更改以适配新的产品,破坏了"开闭原则";
  • 不适合产品过多,且产品数量经常变化的情形,过多的产品将导致工厂内部逻辑复杂混乱。

上述代码可访问Github获取。

以上是关于Java设计模式-简单工厂模式的主要内容,如果未能解决你的问题,请参考以下文章

简单工厂模式

Java设计模式之二工厂模式

Java进阶篇设计模式之二 ----- 工厂模式

简单工厂模式

23种设计模式——简单工厂设计模式

设计模式--简单工厂模式