前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >php设计模式(四):抽象工厂(Abstract Factory)

php设计模式(四):抽象工厂(Abstract Factory)

作者头像
高久峰
发布2023-09-18 15:42:55
1170
发布2023-09-18 15:42:55
举报

抽象工厂

抽象工厂(Abstract Factory)是一种创建型设计模式,它能创建一系列相关的对象,而无需指定其具体类

问题

假设你需要开发一款组装DIY台式电脑的应用,最初只需要拼装一台台式电脑并计算出每台总部件价格即可(简单工厂方法),现在需要组装成品牌机(华硕、联想、…),对于品牌机每个部件都需要属于这个品牌。

通过工厂方法我们需要创建很多的产品工厂类,而且你不留神,可能会给顾客组装错误的部件,如华硕的台式机组装了联想的键盘,这样如果顾客收到的部件不一样,他们会心里万只草泥马。

此外, 你也不希望在添加新部件或新品牌时修改已有代码。品牌机供应对于产品目录的更新非常频繁,你不会想在每次更新时都去修改核心代码的。

解决方法

STEP 1 建立产品

抽象工厂模式为系列中的每个部件明确声明接口(例如键盘、鼠标或显示器)。然后,确保所有部件变体都继承这些接口。例如,所有品牌的鼠标都实现 鼠标 接口;所有品牌的键盘都实现 键盘 接口,以此类推。

STEP 2 声明抽象工厂

声明抽象工厂。例如 createMouse 创建鼠标 、 createKeyboard 创建键盘 和 createDisplay 创建显示器 。 这些方法必须返回抽象产品类型,即我们之前抽取的那些接口: 鼠标 ,沙发 和 显示器 等等。

STEP 3 创建具体工厂

创建具体品牌工厂。例如 AsusComputerAbstractFactory 华硕台式电脑工厂,实现 STEP 2 声明抽象工厂 抽象工厂类接口。

STEP 4 客户端使用

客户端直接使用STEP 3 创建具体品牌工厂具体的工厂即可,无需知道部件是什么品牌。

结构

多个 interface 或者 abstract 产品基类 多个实现 interface 或者继承 abstract 的具体产品类

1个 interface 或者 abstract 工厂基类 1个实现 interface 或者继承 abstract 的具体工厂类

具体的工厂类里面有多个方法分别实例化具体的产品类

代码示例

抽象产品基类

代码语言:javascript
复制
// Keyboard.php
interface Keyboard
{
    public function getPrice();
}

// Mouse.php
interface Mouse
{
    public function getPrice();
}

PHP

Copy

具体产品

华硕电脑

代码语言:javascript
复制
// AsusMouse.php
class AsusMouse implements Mouse
{
    public function getPrice(): float
    {
        return 49.9;
    }
}

// AsusKeyboard.php
class AsusKeyboard implements Keyboard
{
    public function getPrice(): float
    {
        return 149.9;
    }
}

...

PHP

Copy

产品工厂类基类

代码语言:javascript
复制
// AbstractFactory.php
interface AbstractFactory
{
    public function createKeyboard();

    public function createMouse();
}

PHP

Copy

产品工具体厂类

代码语言:javascript
复制
// AsusComputerAbstractFactory.php
class AsusComputerAbstractFactory implements AbstractFactory
{
    public function createKeyboard(): Product
    {
        return new AsusKeyboard();
    }

    public function createMouse(): Product
    {
        return new AsusMouse();
    }
    
    ...
}

PHP

Copy

客户端类

代码语言:javascript
复制
// Client.php
// 华硕工厂类
$asusComputer = new AsusComputerAbstractFactory();

// 鼠标
$mouse = $asusComputer->createMouse();
$mousePrice = $mouse->getPrice();

// 键盘
$keyboard = $asusComputer->createKeyboard();
$keyboardPrice = $keyboard->getPrice();
...

echo $mousePrice + $keyboardPrice + ...;

PHP

Copy

UML

UML
UML

代码

抽象工厂模式代码

优缺点

优点

  • 你可以确保同一工厂生成的产品相互匹配。
  • 你可以避免客户端和具体产品代码的耦合。
  • 单一职责原则。 你可以将产品生成代码抽取到同一位置, 使得代码易于维护。
  • 开闭原则。 向应用程序中引入新产品变体时, 你无需修改客 户端代码。

缺点

  • 工厂需要引入很多新的子类,代码可能会因此变得更复杂。
本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 抽象工厂
  • 问题
  • 解决方法
    • STEP 1 建立产品
      • STEP 2 声明抽象工厂
        • STEP 3 创建具体工厂
          • STEP 4 客户端使用
          • 结构
          • 代码示例
            • 抽象产品基类
              • 具体产品
                • 产品工厂类基类
                  • 产品工具体厂类
                    • 客户端类
                    • UML
                    • 代码
                    • 优缺点
                      • 优点
                        • 缺点
                        领券
                        问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档