Full analysis of Python design patterns
Design patterns are not rigid code templates, but a repeatedly proven framework of ideas for solving common software problems. Python's dynamic types, higher-order functions, metaclasses and other features can just make these ideas more "lightweight" than static languages, and even "invisibly" integrated into daily code.
This article uses Python native syntax or minimalist code to quickly dismantle three types of core design patterns and help you avoid the misunderstanding of "using patterns for the sake of using patterns".
Complete reference implementation library (GitHub Wanxing+): faif/python-patterns
1. Creational Patterns
Core logic: Do not let the caller directlynewOr create objects - encapsulate the creation details, which not only decouples the system and specific classes, but also flexibly controls the method, timing and quantity of instantiation.
1. Factory Method
There is no need to explicitly know the specific class name, "get" the object from the factory function through input parameters or current configuration.
- ✅ Advantages: Shield object creation details, add new formats (such as
yaml) only needs to modify the factory function and does not touch the caller code. - ❌ Disadvantages: Simple scenarios (only 2 optional objects) will increase a little logic cost.
- 📌 Applicable to: Scenarios where instances or tool classes need to be dynamically selected based on configuration.
2. Abstract Factory
The "upgrade model" of the factory is responsible for producing a complete set of related and compatible product families (such as buttons, backgrounds, and fonts in a set of skins) to ensure that they will not "mix and match errors."
- ✅ Advantages: Force the product family to have a unified style, and there will be no low-level errors of "light-colored buttons with black backgrounds".
- ❌ Disadvantages: Expanding the "dimensions of the product family" (such as adding rounded or right angle attributes) is very troublesome and requires changing all factory classes.
- 📌 Applicable to: The connection and query tools are generated when changing the skin system and supporting multiple databases (MySQL / PostgreSQL).
3. Singleton mode (Singleton)
Ensure that a certain class has only one instance globally and provide a unified access entrance. There are many ways to implement Python, here we use the simplest one__new__Magic method:
- ✅ Advantages: Save memory (such as database connection pool, global log manager) and avoid repeated initialization.
- ❌ Disadvantages: It violates the single responsibility principle (managing both its own creation and business data), and requires locking to ensure security in a multi-threaded environment.
- 📌 Applicable to: Configuration management, log system, global unique resource manager.
2. Structural Patterns
Core logic: How to flexibly combine classes or objects to achieve greater functions, instead of using an "inheritance tree" that becomes unmaintainable.
4. Decorator mode (Decorator)
Python comes with@decoratorSyntactic sugar fits this pattern perfectly! **Dynamicly "add functionality" to an object or function without modifying its original source code. **
- ✅ Advantages: More flexible than inheritance (any number of decorators can be superimposed, the order is adjustable), and it fully complies with the opening and closing principle.
- ❌ Disadvantages: Multiple levels of nesting will make debugging difficult (the error stack may point to
wrapper, not intuitive). - 📌 Applicable to: Logging, performance monitoring, permission verification, caching and other aspects of functions.
5. Proxy mode (Proxy)
Add a "substitute" to the target object. The caller accesses the substitute first. The substitute can control access permissions, delay loading of the target object, and even cache results.
- ✅ Advantages: Control access, lazy loading, caching results, and hiding the implementation of real objects.
- ❌ Disadvantages: A layer of middle layer is added, and there will be a very slight loss in calling speed.
- 📌 Applicable to: Image lazy loading, remote service proxy, security control (check user permissions before calling the real object).
3. Behavioral Patterns
Core logic: Focus on how objects communicate and collaborate to make interactions clearer and easier to expand.
6. Iterator pattern (Iterator)
Python native support! No need to manually define complex iterator classes (unless you want to customize traversal logic) - just implement__iter__and__next__Magic method, or directly use the built-initer()、next()。
- ✅ Advantages: Access collection contents without exposing the internal structure, and support multiple traversal methods (such as forward, reverse, depth first, etc.).
- ❌ Disadvantages: For simple lists or dictionaries, manually implementing iterators would be redundant.
- 📌 Applicable to: Traverse database query results, process very large streaming files, and customize data structures.
This article only covers the 6 most commonly used design patterns, and the rest can be studied in depth with the reference code library at the beginning. Remember: Patterns are tools, not purposes - when you encounter a problem, first think about "Is there any ready-made pattern that can be applied", and then decide whether to introduce it and how to use it in the most Pythonic way.

