美文网首页
设计模式 -- 抽象工厂模式

设计模式 -- 抽象工厂模式

作者: 皆为序幕_ | 来源:发表于2019-07-11 17:06 被阅读0次

    表述 (创建型模式)

    提供一个创建一系列相关或者相互依赖对象的接口,而无需指定它们具体的类

    抽象工厂模式和工厂方法模式很相似,是三种工厂模式中最抽象的一种设计模式。抽象工厂模式中定义了抽象工厂类,抽象工厂类中定义了每个系列的抽象类创建的方法,每个工厂子类都对应着一个系列,工厂子类通过重写这些方法来实例化当前系列的抽象子类

    抽象工厂模式类图

    抽象工厂模式类图
    • AbstractFactory(抽象工厂接口):负责创建抽象类
    • ConcreteFactory1和ConcreteFactory2(具体的工厂):继承自抽象工厂类,重写父类定义的对应方法,直接在客户端的使用下创建对应的抽象子类
    • AbstractProductA和AbstractProductB(抽象产品):定义当前类型抽象子类的操作,子类继承父类完成具体的操作
    • ProductA1、ProductA2、ProductB1和ProductB2(具体的产品):抽象子类,继承自对应的抽象类,是客户最终需要的产品,实现抽象类的接口,定制自己实现的逻辑

    优点

    • 切换产品变得容易
    • 封装性,具体的创建实例过程与客户端分离,客户端是通过它们的抽象接口操作实例,产品的具体类名也被具体工厂的实现分离,不会出现在客户代码中

    使用场景

    • 类可以让其子类决定在运行期具体实例化的对象
    • 封装一组相互关联的类的创建
    • 从产品角度讲,如果系统有多于一个的产品族,而系统只消费其中的某一产品;一个系统不应该依赖于产品实例如何被创建、组合和表达的细节,这对于所有形态的工厂模式都是重要的

    示例

    需求V1:现有俩个系列手机iPhone和xiaomi,它们分别有这打电话、发信息这俩个功能

    iPhone 和 xiaomi 属于不同的系列,所以,是俩个不同的工厂子类,俩者都有打电话、发信息功能,每个功能就是一个类型,每个类型就是一个抽象类,因此,iPhone 的打电话抽象子类对应 xiaomi 打电话抽象子类,这俩个抽象子类都属于同一类型,继承同一个抽象类,分别被不同系列的工厂子类创建,在抽象设计模式中,不同系列相同类型的抽象子类都是一一对应的

    抽象类和抽象子类:

    //定义发信息抽象类
    class SendMessage {
        func sendMessage() {
            
        }
    }
    //定义打电话抽象类
    class CallPhone {
        func callPhone() {
            
        }
    }
    
    //抽象子类分别继承不同类型的抽象类,并实现不同系列的持久化代码
    class iPhoneSendMessage : SendMessage {
        override func sendMessage() {
            print("iphone 发信息")
        }
    }
    
    class XiaomiSendMessage : SendMessage  {
        override func sendMessage() {
            print("xiaomi 发信息")
        }
    }
    
    class iPhoneCallPhone : CallPhone {
        override func callPhone() {
            print("iphone 打电话")
        }
    }
    
    class XiaomiCallPhone : CallPhone {
        override func callPhone() {
            print("xiaomi 打电话")
        }
    }
    

    抽象工厂类和工厂子类:

    //定义了俩个抽象接口用来实例化不同类型的抽象类
    class PhoneFactory {
        func createCallPhone() -> CallPhone {
            return CallPhone()
        }
        func createSendMessage() -> SendMessage {
            return SendMessage()
        }
    }
    
    //实现了不同系列的抽象子类实例化
    class iPhoneFactory : PhoneFactory {
        override func createCallPhone() -> CallPhone {
            return iPhoneCallPhone()
        }
        override func createSendMessage() -> SendMessage {
            return iPhoneSendMessage()
        }
    }
    //实现了不同系列的抽象子类实例化
    class XiaomiFactory : PhoneFactory {
        override func createCallPhone() -> CallPhone {
            return XiaomiCallPhone()
        }
        override func createSendMessage() -> SendMessage {
            return XiaomiSendMessage()
        }
    }
    

    客户端调用:

    let iPhoneFac = iPhoneFactory()
    let iphoneCall = iPhoneFac.createCallPhone()
    iphoneCall.callPhone()
    let iphoneSend = iPhoneFac.createSendMessage()
    iphoneSend.sendMessage()
    
    let xiaomiFac = XiaomiFactory()
    let xiaomiCall = xiaomiFac.createCallPhone()
    xiaomiCall.callPhone()
    let xiaomiSend = xiaomiFac.createSendMessage()
    xiaomiSend.sendMessage()
    

    需求V2:假设在原有需求上又加入了一个功能,俩个系列的手机都有打游戏的功能

    根据需求V2,需要增加了打游戏,那么就是增加了一个类型,所以我们需要新增一个抽象类,同时需要更改抽象工厂和工厂子类

    新增抽象类:

    class PlayGame {
        func playGame() {
            
        }
    }
    class iPhonePlayGame : PlayGame {
        override func playGame() {
            print("iphone 打游戏")
        }
    }
    class XiaomiPlayGame : PlayGame {
        override func playGame() {
            print("xiaomi 打游戏")
        }
    }
    

    修改后的抽象工厂和工厂子类:

    //定义了俩个抽象接口用来实例化不同类型的抽象类
    class PhoneFactory {
        func createCallPhone() -> CallPhone {
            return CallPhone()
        }
        func createSendMessage() -> SendMessage {
            return SendMessage()
        }
        func createPlaygame() -> PlayGame {
            return PlayGame()
        }
    }
    
    //实现了不同系列的抽象子类实例化
    class iPhoneFactory : PhoneFactory {
        override func createCallPhone() -> CallPhone {
            return iPhoneCallPhone()
        }
        override func createSendMessage() -> SendMessage {
            return iPhoneSendMessage()
        }
        override func createPlaygame() -> PlayGame {
            return iPhonePlayGame()
        }
        
    }
    //实现了不同系列的抽象子类实例化
    class XiaomiFactory : PhoneFactory {
        override func createCallPhone() -> CallPhone {
            return XiaomiCallPhone()
        }
        override func createSendMessage() -> SendMessage {
            return XiaomiSendMessage()
        }
        override func createPlaygame() -> PlayGame {
            return XiaomiPlayGame()
        }
    }
    

    客户端调用:

    let iPhoneFac = iPhoneFactory()
    let iphonePaly = iPhoneFac.createPlaygame()
    iphonePaly.playGame()
    let xiaomiFac = XiaomiFactory()
    let xiaomiPlay = xiaomiFac.createPlaygame()
    xiaomiPlay.playGame()
    

    需求V3: 假设在原有需求上又加入了一个新款手机OPPO,并且它支持打电话、发信息、打游戏的功能

    根据需求V3,需要分别继承三个原来的抽象类,新建三个抽象子类,因为加入的是一个新的系列,所以还需要新增一个工厂子类,原抽象工厂保持不变

    新增抽象子类:

    class OppoCallPhone : CallPhone {
        override func callPhone() {
            print("oppo 打电话")
        }
    }
    class OppoSendMessage : SendMessage {
        override func sendMessage() {
            print("oppo 发信息")
        }
    }
    class OppoPlayGame : PlayGame {
        override func playGame() {
            print("oppo 打游戏")
        }
    }
    

    新增工厂子类:

    class OppoFactory : PhoneFactory {
        override func createCallPhone() -> CallPhone {
            return OppoCallPhone()
        }
        override func createSendMessage() -> SendMessage {
            return OppoSendMessage()
        }
        override func createPlaygame() -> PlayGame {
            return OppoPlayGame()
        }
    }
    

    客户端调用:

    let oppoFac = OppoFactory()
    let oppoCall = oppoFac.createCallPhone()
    oppoCall.callPhone()
    let oppoSend = oppoFac.createSendMessage()
    oppoSend.sendMessage()
    let oppoPaly = oppoFac.createPlaygame()
    oppoPaly.playGame()
    

    可以看出在新加系列产品或新加功能类型的需求下,都违背开放-封闭原则,而且要增加2-3新类,所以需要在适合的业务场景使用这种模式,否则会适得其反

    相关文章

      网友评论

          本文标题:设计模式 -- 抽象工厂模式

          本文链接:https://www.haomeiwen.com/subject/mxqsxctx.html