Why should anyone use flyweight design pattern?

Hardik Patel
3 min readAug 11, 2024

--

The Flyweight design pattern is a structural pattern that allows you to reduce the memory footprint of your application by minimizing the number of required objects. It’s useful when you have a large number of similar objects that share some common properties. In this article, we’ll explore the Flyweight pattern in detail and provide a Python example to illustrate its implementation.

What is the Flyweight Pattern?

The Flyweight pattern is a design pattern that aims to reduce the memory usage of an application by sharing common properties among multiple objects. It does this by separating the intrinsic and extrinsic properties of an object.

  • Intrinsic Properties: These are the properties that define the object’s identity and are shared among multiple objects.
  • Extrinsic Properties: These are the properties that are unique to each object and are not shared.

Components of the Flyweight Pattern

The Flyweight pattern consists of the following components:

  • Flyweight: This is the interface or abstract class that defines the intrinsic properties of the object.
  • Concrete Flyweight: This is the concrete implementation of the Flyweight interface.
  • Unshared Concrete Flyweight: This is the concrete implementation of the Flyweight interface that has unique extrinsic properties.
  • Flyweight Factory: This is the factory class that creates and manages the Flyweight objects.

Example

Let’s consider a simple example of a smartphone factory that produces smartphones with different properties like brand, model, color, and storage capacity. We can use the Flyweight pattern to optimize the memory usage of our application.

Python

from typing import List, Dict


class SmartPhone:
"""
Smartphone(Flyweight)
"""
def __init__(self, properties: List) -> None:
self._properties = properties
def sell(self, owner: str, price: int) -> None:
"""
Selling operation on smartphone(flyweight object)
which takes unique values per smartphone
"""
common = self._properties
print(f"Smartphone {common} is sold to {owner} for price {price}")
def __repr__(self) -> str:
return f'SmartPhone(properties={self._properties})'
class SmartPhoneFactory:
"""
Smartphone(flyweight) factory
"""
_smartphones: Dict[str, SmartPhone] = {}
def get_smartphone(self, properties: List) -> SmartPhone:
"""
Return smartphone(flyweight) object
This method creates new object and cache it if doesn't exist
"""
key = '-'.join(properties)
if key in self._smartphones:
print(f"Returning already existing Smartphone object for {properties}")
else:
print(f"New Smartphone object created for {properties}")
self._smartphones[key] = SmartPhone(properties)
return self._smartphones[key]
def list_smartphones(self) -> List[SmartPhone]:
"""
List down all the smartphones
"""
smartphones = self._smartphones.values()
for item in smartphones:
print(item)
if __name__ == '__main__':
fact = SmartPhoneFactory()
smartphone = fact.get_smartphone(['Apple', 'iPhone 14', 'Black', '128 GB'])
smartphone.sell('Hardik', 59000)
smartphone = fact.get_smartphone(['Apple', 'iPhone 13', 'Black', '128 GB'])
smartphone.sell('Aarav', 49000)
smartphone = fact.get_smartphone(['Samsung', 'Galaxy S23', 'White', '128 GB'])
smartphone.sell('Shailaja', 63000)
smartphone = fact.get_smartphone(['Apple', 'iPhone 14', 'Black', '128 GB'])
smartphone.sell('Aarav', 59000)
fact.list_smartphones()

In this example, we have a SmartPhone class that represents the flyweight object, and a SmartPhoneFactory class that acts as the factory to create and manage these objects. The SmartPhone class has intrinsic properties like brand, model, color, and storage capacity, which are shared among multiple objects. The SmartPhoneFactory class creates and caches the SmartPhone objects to minimize memory usage.

Benefits of the Flyweight Pattern

The Flyweight pattern offers several benefits, including:

  • Memory Optimization: By sharing common properties among multiple objects, the Flyweight pattern reduces the memory footprint of an application.
  • Improved Performance: With fewer objects to manage, the application can perform better and faster.
  • Simplified Object Management: The Flyweight pattern makes it easier to manage a large number of objects, as you only need to worry about the shared properties.

When to Use Flyweight

The Flyweight pattern is particularly useful in scenarios where:

  • You have a large number of objects with similar properties.
  • Memory usage is a concern.
  • Objects have both intrinsic and extrinsic properties.

Conclusion

In conclusion, the Flyweight design pattern is a useful technique for optimizing memory usage in applications with a large number of similar objects. By separating intrinsic and extrinsic properties, Flyweight allows you to share common properties among multiple objects, reducing memory usage and improving performance.

--

--

No responses yet