前言:
學習python有一段時間,之前就是看看書,最後發現只有實踐才能真正學到東西,只有在解決問題中才能真正掌握. 之前大牛也有用python實現各種設計模式的,我自己參考之前在學習用C#實現設計模式的經歷,也想把23種模式逐一實踐,從網上查了一些資料,才明白python 雖然是面向對象的,但是和C#,java語言不太一樣。影響設計方法不一樣有以下幾點:
有了以上的不同,就注定python在運用設計模式上與其他面向對象語言的不同,下面是我嘗試的實現。《Design Patterns》一書把設計模式分為了3大類,創建型模式(creational pattern)、結構型模式(structural pattern)和 行為型模式(behavioral patterns)。
創建型模式(creational pattern)
對類的實例化過程進行了抽象,能夠使軟件模塊做到與對象創建和組織的無關性。為了使體系結構更加清晰,一些軟件在設計上要求當創建類的具體實例時,能夠根據具體的語境來動態地決定怎樣創建對象,創建哪些對象,以及怎樣組織和表示這些對象,而創建型模式所要描述的就是該如何來解決這些問題。創建型模式包括以下幾種:
- Simple Factory 模式
- Factory Method 模式
- Abstract Factory 模式
- Singleton 模式
- Builder 模式
- Prototype 模式
本次先實踐 Simple Factory 模式,Factory Method 模式 和 Abstract Factory模式,其他模式後續會涉及。
1.Simple Factory模式
Simple Factory模式不是獨立的設計模式,他是Factory Method模式的一種簡單的、特殊的實現。他也被稱為靜態工廠模式,通常創建者的創建方法被設計為static方便調用,但是python沒有static一說。所以可以把創建者也就是工廠設計為一個普通class或全局函數即可。如果是class還需要實例化才能調用工廠方法,而全局函數比較簡單,比較接近靜態工廠的簡便特性。
Simple Factory模式包含以下角色部分,UML可參考下圖:
一個 Simple Factory 模式代碼實例如下:
- SimpleFactory_test.py
- #!/usr/bin/env python
- class car:
- ''' interface as Product '''
- def drive(self):
- pass
- class BMW(car):
- ''' Concrete Product '''
- def __init__ (self,carname):
- self. __name = carname
- def drive(self):
- print " Drive the BMW as " +self. __name
- class Benz(car):
- ''' Concrete Product '''
- def __init__ (self,carname):
- self. __name = carname
- def drive(self):
- print " Drive the Benz as " +self. __name
- class driver:
- ''' Factory also called Creator '''
- def driverCar(self,name):
- if name== "BMW" :
- return BMW( "BMW" )
- elif name== "Benz" :
- return Benz( "Benz" )
- else:
- raise MyInputException(name)
- class MyInputException(Exception) :
- def __init__ (self, name):
- Exception. __init__ (self)
- self.name = name
- if __name__ == "__main__" :
- print " please input \"BMW\" or \"Benz\" : "
- carname= raw_input()
- dier= driver()
- try :
- d= dier.driverCar(carname)
- except MyInputException,e:
- print " input worry name " + e.name
- else :
- d.drive ()
工廠方法模式去掉了簡單工廠模式中工廠方法的靜態屬性,使得它可以被子類繼承。對於python來說,就是工廠類被具體工廠繼承。這樣在簡單工廠模式裡集中在工廠方法上的壓力可以由工廠方法模式裡不同的工廠子類來分擔。也就是工廠外面再封裝一層。
一個Factory Method代碼實例:
- FactoryMethod_test.py
- #!/usr/bin/env python
- class car:
- ''' interface as Product '''
- def drive(self):
- pass
- class BMW(car):
- ''' Concrete Product '''
- def __init__(self,carname):
- self.__name= carname
- def drive(self):
- print " Drive the BMW as " + self.__name
- class Benz(car):
- ''' Concrete Product '''
- def __init__(self,carname):
- self.__name= carname
- def drive(self):
- print " Drive the Benz as " + self.__name
- class driver:
- ''' Factory also called Creator '''
- def driverCar(self):
- return car()
- class BMWdriver(driver):
- ''' Concrete Creator '''
- def driverCar(self):
- return BMW( "BMW" )
- class Benzdriver(driver):
- ''' Concrete Creator '''
- def driverCar(self):
- return Benz( "Benz" )
- if __name__ == "__main__" :
- driver= BMWdriver()
- car= driver.driverCar()
- car.drive()
- driver= Benzdriver()
- car= driver.driverCar()
- car.drive()
抽象工廠是工廠模式的進一步延伸,產品的類變的更加複雜,也就說產品不只是一個接口或父類而是有多個接口和父類了,形成了一個產品族的概念。模式的角色與Factory Method基本一樣,UML 圖如下:
抽象工廠模式的用意為:給客戶端提供一個接口,可以創建多個產品族中的產品對象。 不過使用抽象工廠是有條件的:
簡單的實現代碼如下:
- AbstractFactory_test.py
- #!/usr/bin/env python
- class Newcar:
- ''' Abstract Product '''
- def drive(self):
- pass
- class NewBMW(Newcar):
- ''' Concrete Product '''
- def __init__(self,carname):
- self .__name= carname
- def drive(self):
- print " Drive the New BMW as " + self.__name
- class NewBenz(Newcar):
- ''' Concrete Product '''
- def __init__(self,carname):
- self.__name= carname
- def drive(self):
- print " Drive the New Benz as " + self.__name
- class Oldcar:
- ''' Abstract Product '''
- def drive(self):
- pass
- class OldBMW(Oldcar):
- ''' Concrete Product '''
- def __init__(self,carname):
- self.__name= carname
- def drive(self):
- print " Drive the Old BMW as " + self. __name
- class OldBenz(Oldcar):
- ''' Concrete Product '''
- def __init__(self,carname):
- self.__name= carname
- def drive(self):
- print " Drive the Old Benz as " + self.__name
- class driver:
- ''' Abstract Factory also called Creator '''
- def driverNewCar(self):
- return Newcar()
- def driverOldCar(self):
- return Oldcar()
- class BMWdriver(driver ):
- ''' Concrete Factory or Creator '''
- def driverNewCar(self):
- return NewBMW( "NewBMW" )
- def driverOldCar(self):
- return OldBMW( "OldBMW" )
- class Benzdriver(driver) :
- ''' Concrete Factory or Creator '''
- def driverNewCar(self):
- return NewBenz( "NewBenz" )
- def driverOldCar(self):
- return OldBenz( "OldBenz" )
- if __name__ == "__main__" :
- driver= BMWdriver()
- car= driver.driverNewCar()
- car.drive()
- car= driver.driverOldCar()
- car.drive()
- driver= Benzdriver()
- car= driver.driverNewCar()
- car.drive()
- car= driver.driverOldCar()
- car.drive()
* [OO 設計模式] Simple Factory Pattern : 透過靜態方法來產生物件
* [OO 設計模式] Factory Method Pattern : 工廠方法模式
* [OO 設計模式] Gossip@DesignPattern : Creational - Abstract Factory 模式
* [OO 設計模式] Gossip@DesignPattern : Creational - Builder 模式
沒有留言:
張貼留言