总目录
前言
本文是个人基于C#学习设计模式总结的学习笔记,希望对你有用!
在简单工厂模式中说到了简单工厂模式的缺点:简单工厂模式系统难以扩展,一旦添加新产品就不得不修改简单工厂方法,这样就会造成简单工厂的实现逻辑过于复杂。而工厂方法模式可以很好的规避掉这个缺点,下面就好好研究下工厂方法模式是如何做到的吧!
1 基本介绍
- 工厂方法模式 :一种更高级的工厂模式,具体实现由子类负责,因此更加灵活。这种设计方式符合开闭原则,即对扩展开放,对修改封闭。
工厂方法模式之所以可以解决简单工厂的模式,是因为它的实现把具体产品的创建推迟到子类中,此时工厂类不再负责所有产品的创建,而只是给出具体工厂必须实现的接口,这样工厂方法模式就可以允许系统不修改工厂类逻辑的情况下来添加新产品,这样也就克服了简单工厂模式中缺点,很好地符合了开放封闭原则(即对扩展开发,对修改封闭)。
- 工厂方法模式的主要角色:
抽象工厂
- 在抽象工厂类中声明了工厂方法,用于返回一个产品。提供了创建产品的接口,调用者通过它访问具体工厂的工厂方法来创建产品。
具体产品工厂:
- 它是抽象工厂类的子类,实现了在抽象工厂中声明的工厂方法,完成具体产品的创建。并可由客户端调用,返回一个具体产品类的实例。
抽象产品(抽象类):
- 定义了产品的规范,描述了产品的主要特征和功能。
- 它是工厂类创建的所有对象的父类,封装了各种产品对象的共有方法。
具体产品(实现类):
- 它实现了抽象产品接口,某种类型的具体产品由专门的具体工厂创建,具体工厂和具体产品之间一一对应。
2 适用场景
适用于创建对象需要大量重复的步骤,或者需要依赖于其它对象的情况,它提供了一种方式来封装多个相关或依赖对象的创建逻辑。
- 当工厂类负责创建的对象比较多时可以考虑使用工厂方法模式
3 实现方式
接着张三的案例,张三由原先的自己做鞋子,到后来去鞋厂买鞋子,这样已经让张三特别的省事省力了,但是随着时间变化小镇子的崛起,人们越来又有钱了,小镇子里也住进来更多的人,对于鞋子的种类需求和数量需求越来越多了,之前的小鞋厂已经不能满足需求了,于是鞋厂老板大手一挥,反正这些年也挣了不少米,我们再开几个分厂,我们总厂只负责管理分厂,给分厂技术就可以了,不再负责造鞋的工作了!
假如我们有个抽象产品:鞋子(所有种类鞋子的父类),鞋子内有个抽象方法Show
//抽象父类,抽象产品
public abstract class AbstractShoes
{
//该方法负责输出 产品名称
public abstract void Show();
}
现在该产品有两个子类:LeatherShoes(皮鞋)和GymShoes(体育鞋)
public class LeatherShoes : AbstractShoes
{
public override void Show()
{
Console.WriteLine($"我是:{nameof(LeatherShoes)} !");
}
}
public class GymShoes : AbstractShoes
{
public override void Show()
{
Console.WriteLine($"我是:{nameof(GymShoes)} !");
}
}
鞋子产品这一块的代码不需要改动,主要改动在造鞋工厂。
在还是简单工厂的模式下,简单工厂是负责所有鞋子的生产,代码如下:
//定义一个造鞋工厂类,专门负责生产鞋子
public class ShoesFactory
{
//定义一个公有的静态方法,传入鞋子类别,然后返回一个具体类型的鞋子实例
public static AbstractShoes MakeShoes(string type)
{
if (type == "LeatherShoes")
{
return new LeatherShoes();
}
else if (type == "GymShoes")
{
return new GymShoes();
}
else
{
throw new ArgumentException("Invalid type.");
}
}
}
如上面所说:随着时间变化小镇子的崛起,人们越来又有钱了,小镇子里也住进来更多的人,对于鞋子的种类需求和数量需求越来越多了,之前的小鞋厂已经不能满足需求了,于是鞋厂老板大手一挥,反正这些年也挣了不少米,我们再开几个分厂,每个厂负责制造不同的鞋子,我们总厂只负责管理分厂,给分厂技术就可以了,不再负责造鞋的工作了!
于是就有了如下的改造代码:
//抽象工厂,负责定义实现类需要实现的方法
public abstract class AbstractShoesFactory
{
//定义一个抽象方法
//当下场景下:表示我的分厂必须都会造鞋这些技能,至于怎么造鞋,由分厂自己实现
public abstract AbstractShoes MakeShoes();
}
//具体工厂,负责实现抽象工厂
public class LeatherShoesFactory : AbstractShoesFactory
{
//实现父类的方法
//这是一个皮鞋工厂,需要在实现具体造鞋过程
public override AbstractShoes MakeShoes()
{
return new LeatherShoes();
}
}
//具体工厂
public class GymShoesFactory : AbstractShoesFactory
{
public override AbstractShoes MakeShoes()
{
return new GymShoes();
}
}
此时当张三再去买些的时候,就变成了如下的模式:
public class ZhangSan
{
public void Main()
{
//初始化不同种类的鞋子工厂
AbstractShoesFactory abstractShoesFactory1 = new LeatherShoesFactory();
AbstractShoesFactory abstractShoesFactory2 = new GymShoesFactory();
//用皮鞋工厂的实例,制造皮鞋
AbstractShoes abstractShoes1 = abstractShoesFactory1.MakeShoes();
abstractShoes1.Show();
//用体育鞋工厂的实例,制造体育鞋
AbstractShoes abstractShoes2 = abstractShoesFactory2.MakeShoes();
abstractShoes2.Show();
}
}
在这里我们发现,不需要在新增一个产品的时候,去改动简单工厂内的方法(违背开闭原则);
在新增一个产品的时候,我们只需要对应新增一个新的产品类和生产该产品的工厂类即可,而不需要再去核心的工厂类中去进行代码的修改,这个符合开闭原则,对扩展开发,对修改关闭。
4 优缺点分析
简单工厂把全部的事情(变化的因素),在一个地方(类)全部处理完;而工厂方法则会定义一个用于创建对象的接口,让子类决定实例化哪个产品类对象。工厂方法使一个产品类的实例化延迟到其工厂的子类。这样一来,扩展产品种类就不必修改工厂函数了,核心类就变成抽象类,工厂方法模式将生成具体产品的任务分发给具体的产品工厂。也就是相当于工厂总部不生产产品了,交给下辖分工厂进行生产。要增加产品类时也要相应地增加工厂类,不需要修改工厂类的代码了,这样就解决了简单工厂模式的缺点。工厂方法模式是简单工厂模式的进一步抽象。由于使用了多态性,工厂方法模式保持了简单工厂模式的优点,而且克服了它的缺点。
- 优点:实现了对象的创建和使用分离且符合开闭原则,使得代码更加灵活和可维护
- 缺点:每增加一个产品就要增加一个具体产品类和一个对应的具体工厂类,这增加了系统的复杂度。
结语
以上就是本文的内容,希望以上内容可以帮助到大家,如文中有不对之处,还请批评指正。