• 设计模式-创建型-抽象工厂模式


      前一章节,我们介绍了简单工厂模式以及工厂方法模式,但是这两种模式都存在一定的局限性,只能生产某一类型下的某一种产品,如果需求变更,同类型下出现了不同的产品,比如芝士披萨不仅有口味上的不同,同时存在外观上的不同。这种时候,工厂模式显然不再满足要求,该怎么办呢?于是我们想到DIP原则,它不正是为了解决这种情况而存在的吗?接下来我们来介绍下抽象工厂模式:

      1、抽象工厂模式定义了一个interface用于创建相关或有依赖关系的对象簇,而无需指明具体的类。

      2、抽象工厂模式可以将简单工厂模式和工厂方法模式进行整合。

      3、从设计层面来说,抽象工厂模式就是对简单工厂模式的改进(即进一步抽象化)

      4、将工厂抽象成两层,抽象工厂和具体的实现工厂。

    还是拿pizza订购举例,我们定义一个抽象工厂AbsFactory,由子类工厂实现该抽象工厂;订购披萨OrderPizza依赖抽象,不依赖具体的实现。

       

      1 internal class Program
      2 {
      3     private static void Main(string[] args)
      4     {
      5         new OrderPizza(new BJFactory());
      6     }
      7 }
      8 
      9 internal class OrderPizza
     10 {
     11     private AbsFactory factory;
     12 
     13     public OrderPizza(AbsFactory factory)
     14     {
     15         setFactory(factory);
     16         Order();
     17     }
     18 
     19     private void setFactory(AbsFactory factory)
     20     {
     21         this.factory = factory;
     22     }
     23 
     24     private void Order()
     25     {
     26         Pizza pizza = null;
     27         string orderType = "";
     28         do
     29         {
     30             Console.Write("请输入订购类型:");
     31             orderType = Console.ReadLine();
     32             pizza = this.factory.createPizza(orderType);
     33             if (pizza == null)
     34             {
     35                 Console.WriteLine("订购失败");
     36                 break;
     37             }
     38             //开始制作
     39             pizza.prepare();
     40             pizza.bake();
     41             pizza.cut();
     42             pizza.box();
     43         } while (true);
     44     }
     45 }
     46 
     47 internal interface AbsFactory
     48 {
     49     Pizza createPizza(string orderType);
     50 }
     51 
     52 internal class BJFactory : AbsFactory
     53 {
     54     public Pizza createPizza(string orderType)
     55     {
     56         Pizza pizza = null;
     57         if (orderType == "cheese")
     58         {
     59             pizza = new BJCheesePizza();
     60             pizza.setName("北京芝士披萨");
     61         }
     62         else if (orderType == "greek")
     63         {
     64             pizza = new BJGreekPizza();
     65             pizza.setName("北京希腊披萨");
     66         }
     67         return pizza;
     68     }
     69 }
     70 
     71 internal class LDFactory : AbsFactory
     72 {
     73     public Pizza createPizza(string orderType)
     74     {
     75         Pizza pizza = null;
     76         if (orderType == "cheese")
     77         {
     78             pizza = new LDCheesePizza();
     79             pizza.setName("伦敦芝士披萨");
     80         }
     81         else if (orderType == "greek")
     82         {
     83             pizza = new LDGreekPizza();
     84             pizza.setName("伦敦希腊披萨");
     85         }
     86         return pizza;
     87     }
     88 }
     89 
     90 internal abstract class Pizza
     91 {
     92     private string name;
     93 
     94     public abstract void prepare();
     95 
     96     public void bake()
     97     {
     98         Console.WriteLine($"{this.name} 烘培");
     99     }
    100 
    101     public void cut()
    102     {
    103         Console.WriteLine($"{this.name} 修剪");
    104     }
    105 
    106     public void box()
    107     {
    108         Console.WriteLine($"{this.name} 打包");
    109     }
    110 
    111     public void setName(string name)
    112     {
    113         this.name = name;
    114     }
    115 }
    116 
    117 internal class BJCheesePizza : Pizza
    118 {
    119     public override void prepare()
    120     {
    121         Console.WriteLine("北京的芝士披萨准备中");
    122     }
    123 }
    124 
    125 internal class BJGreekPizza : Pizza
    126 {
    127     public override void prepare()
    128     {
    129         Console.WriteLine("北京的希腊披萨准备中");
    130     }
    131 }
    132 
    133 internal class LDCheesePizza : Pizza
    134 {
    135     public override void prepare()
    136     {
    137         Console.WriteLine("伦敦的芝士披萨准备中");
    138     }
    139 }
    140 
    141 internal class LDGreekPizza : Pizza
    142 {
    143     public override void prepare()
    144     {
    145         Console.WriteLine("伦敦的希腊披萨准备中");
    146     }
    147 }
    view code

    读过一些博主的博文以及评论,有一些理解还是蛮到位的:

      1、抽象工厂比工厂方法复杂的多,它们的目的不同。工厂方法意在延迟加载,而抽象方法意在高内聚低耦合。

      2、工厂方法模式的具体工厂类只能创建一个具体产品类的实例,而抽象工厂可以创建多个。

    参考:https://www.runoob.com/design-pattern/abstract-factory-pattern.html

  • 相关阅读:
    sqlserver数据库备份还原时出现3241问题
    ssms安装失败_拒绝访问0x80070005解决方法
    Linux strace命令
    争议 | 要不要去IT外包公司工作?
    sqlserver计算时间差DATEDIFF 函数
    CodeForces
    [HNOI 2016] 网络
    CodeForces
    AtCoder Beginner Contest 209
    学习4412开发板+项目实战+配套视频+每日指导
  • 原文地址:https://www.cnblogs.com/az4215/p/11518442.html
Copyright © 2020-2023  润新知