- Mastering JavaScript Design Patterns
- Simon Timms
- 760字
- 2021-08-05 17:14:59
Factory Method
We've already looked at the Abstract Factory and Builder patterns. The Abstract Factory pattern builds a family of related classes and the builder creates complicated objects using different strategies. The Factory Method pattern allows a class to request a new instance of an interface without the class making decisions about which implementation of the interface to use. The factory may use some strategy to select which implementation to return. This is shown in the following diagram:

Sometimes, this strategy is simply to take a string parameter or to examine some global setting to act as a switch.
Implementation
In our example world of Westeros
, there are plenty of times when we would like to defer the choice of implementation to a factory. Just like the real world, Westeros has a vibrant religious culture with dozens of competing religions worshiping a wide variety of gods. When praying in each religion, different rules must be followed. Some religions demand sacrifices while others demand only that a gift be given. The prayer class doesn't want to know about all the different religions and how to construct them.
Let's start with creating a number of different gods to which prayers can be offered. The following code creates three gods, including a default god to whom prayers fall if no other god is specified:
var WateryGod = (function () { function WateryGod() { } WateryGod.prototype.prayTo = function () { }; return WateryGod; })(); Religion.WateryGod = WateryGod; var AncientGods = (function () { function AncientGods() { } AncientGods.prototype.prayTo = function () { }; return AncientGods; })(); Religion.AncientGods = AncientGods; var DefaultGod = (function () { function DefaultGod() { } DefaultGod.prototype.prayTo = function () { }; return DefaultGod; })(); Religion.DefaultGod = DefaultGod;
I've avoided any sort of implementation details for each god. You may imagine whatever traditions you want to populate the prayTo
methods. There is also no need to ensure that each of the gods implements an IGod
interface. Next, we'll need a factory that is responsible for constructing each of the different gods, as shown in the following code:
var GodFactory = (function () { function GodFactory() { } GodFactory.Build = function (godName) { if (godName === "watery") return new WateryGod(); if (godName === "ancient") return new AncientGods(); return new DefaultGod(); }; return GodFactory; })();
You can see that, in this example, we're taking in a simple string to decide how to create a god. It could be done via a global or via a more complicated object. In some polytheistic religions in Westeros, gods have defined roles as gods of courage, beauty, or some other aspect. The god to which one must pray is determined by not just the religion but the purpose of the prayer. We can represent this with a GodDeterminant
class, as shown in the following code:
var GodDeterminant = (function () { function GodDeterminant(religionName, prayerPurpose) { this.religionName = religionName; this.prayerPurpose = prayerPurpose; } return GodDeterminant; })();
The factory would be updated to take this class instead of the simple string.
Finally, the last step is to see how this factory would be used. It is quite simple; we just need to pass in a string that denotes which religion we wish to observe and the factory will construct the correct god and return it. The following code demonstrates how to call the factory:
var Prayer = (function () { function Prayer() { } Prayer.prototype.pray = function (godName) { GodFactory.Build(godName).prayTo(); }; return Prayer; })();
Once again, there is certainly need for a pattern such as this in JavaScript. There are plenty of times when separating the instantiation from the use is useful. Testing the instantiation is also very simple thanks to the separation of concerns, and the ability to inject a fake factory to allow testing of the Prayer
class is also easy.
Continuing the trend of creating simpler patterns without interfaces, we can ignore the interface portion of the pattern and work directly with the types, thanks to duck typing.
Factory Method is a very useful pattern; it allows classes to defer the selection of the implementation of an instantiation to another class. This pattern is very useful when there are multiple similar implementations such as the strategy pattern (see Chapter 5, Behavioral Patterns), and is commonly used in conjunction with the Abstract Factory pattern. The Factory Method pattern is used to build the concrete objects within a concrete implementation of the Abstract Factory. An Abstract Factory may contain a number of factory methods. Factory Method is certainly a pattern that remains applicable in the field of JavaScript.
- UML和模式應用(原書第3版)
- Learning Selenium Testing Tools with Python
- Mastering Apache Spark 2.x(Second Edition)
- Mastering JBoss Enterprise Application Platform 7
- Java EE核心技術與應用
- Julia高性能科學計算(第2版)
- Advanced Express Web Application Development
- Java Fundamentals
- JavaScript腳本特效編程給力起飛
- Python商務數據分析(微課版)
- 數據分析與挖掘算法:Python實戰
- Java高手是怎樣煉成的:原理、方法與實踐
- 零基礎學編程系列(全5冊)
- 用Go語言自制編譯器
- 第五空間戰略:大國間的網絡博弈