CP1 - Vending Machine (Factory) - Design Pattern From Simple Things
Different beverages are scattered in different stores, it's too tiring to run through each store to find your beverage. You wish all beverages were sold in one place.
Vending Machine (Factory) is a creational design pattern: 🖤🖤🖤🖤🖤
Although widely used,
(Simple) Factoryis not part of the GoF Design Pattern. It’s a term for a class creating objects without requiring any concrete classes.
Factoryis too vague for me, so I useVending Machineinstead! Vending Machine is the same as Factory, but it’s more friendly :)
What is Vending Machine?
Beverage Vending Machine is a store holding a variety of beverages(Pepsi, Coke, Monster)
Just enter beverage ID(1, 2, 3) to Beverage Vending Machine, then Beverage Vending Machine will return your beverage.
Why use Vending Machine?
It makes finding your beverage easier!
Question: I hate the Beverage Vending Machine, but I want to buy a Coke right now because I’m bloating.
Answer: You can find your Coke by searching in stores. If a store doesn’t sell it, try to find it again by going to another store, try again until you find it 🙂
When to use Vending Machine?
Question: When do I go to the Beverage Vending Machine?
Answer: When you need a beverage Pepsi, Coke or Monster, right?
Input:
- Having a menu of beverages:
Pepsi (ID = 1)Coke (ID = 2)Monster (ID = 3)
- Beverages are being sold.
- Knowing the beverage you need to buy
Coke.
import abc
# Input 1: Having a menu of beverages:
class MENU:
PEPSI = 1
COKE = 2
MONSTER = 3
class Beverage(metaclass=abc.ABCMeta):
id = ""
carbon_dioxide = 0
# @abc.abstractmethod means: in the concrete class, The method have to re-defined
@abc.abstractmethod
def make_burp(self):
return ""
# Input 2: Beverages are being sold.
class Pepsi(Beverage):
id = MENU.PEPSI
carbon_dioxide = 3
def make_burp(self):
return f"B{'U' * self.carbon_dioxide}RP"
# Input 2: Beverages are being sold.
class Coke(Beverage):
id = MENU.COKE
carbon_dioxide = 2
def make_burp(self):
return f"BU{'R' * self.carbon_dioxide}P"
# Input 2: Beverages are being sold.
class Monster(Beverage):
id = MENU.MONSTER
carbon_dioxide = 1
def make_burp(self):
return f"BURP"
Expected Output:
- Get a beverage
Coke - Drink your beverage and make a burp
BURRP - Get all carbonated_beverages
generate a beverage by id
<Coke object>
BURRP
generate all carbonated beverages
[<Pepsi object>, <Coke object>]
How to implement Vending Machine?
Non-Vending Machine implementation:
if __name__ == "__main__":
print("generate a beverage by id")
beverage = None
for beverage_cls in [Pepsi, Coke, Monster]:
# Input 3: Knowing the beverage you need to buy.
if MENU.COKE == beverage_cls.id:
beverage = beverage_cls()
# Expected Output 1: Get a beverage
print(beverage)
# Expected Output 2: Drink your beverage and make a burp
print(beverage.make_burp())
print("generate all carbonated beverages")
carbonated_beverages = []
for beverage_cls in [Pepsi, Coke, Monster]:
if beverage_cls.carbon_dioxide > 1:
carbonated_beverages.append(beverage_cls())
print(carbonated_beverages)
Vending Machine implementation:
class BeverageVendingMachine:
@property
def subclasses(self):
# [<class 'Pepsi'>, <class 'Coke'>, <class 'Monster'>]
return Beverage.__subclasses__()
@property
def subclass_mapping(self):
# {1: <class 'Pepsi'>, 2: <class 'Coke'>, 3: <class 'Monster'>}
return {beverage.id: beverage for beverage in self.subclasses}
def generate(self, key):
subclass = self.subclass_mapping[key]
instance = subclass()
return instance
@property
def generate_carbonated_beverages(self):
return [subclass() for subclass in self.subclasses if subclass.carbon_dioxide > 1]
if __name__ == "__main__":
beverage_vending_machine = BeverageVendingMachine()
print("generate a beverage by id")
# Input 3: Knowing the beverage you need to buy.
coke = beverage_vending_machine.generate(MENU.COKE)
# Expected Output 1: Get a beverage
print(coke)
# Expected Output 2: Drink your beverage and make a burp
print(coke.make_burp())
print("generate all carbonated beverages")
carbonated_beverages = beverage_vending_machine.generate_carbonated_beverages
print(carbonated_beverages)
Related posts
-
Verify vs Cert: The Python Requests Handbook
Understanding SSL/TLS in Python Requests: The 'verify' and 'cert' arguments explained with interactive animations.
-
SP7 - Proxy - Learn Design Pattern From Simple Things
The boss wants the employees to focus on work and not get distracted by social media. So he decides to block some websites on the corporate network during working hours.
-
SP6 - Object Pool - Learn Design Pattern From Simple Things
Producing planes on a large scale is expensive, but fortunately the manufactured raw parts are always stored in the pool, thereby reducing duplication in the production process.
-
SP5 - Facade - Learn Design Pattern From Simple Things
There are many departments in the building and you feel confused! By opening the entrances from the facade according to purposes, you simply follow the pre-arranged flow.