Exploring Design Patterns: Singleton

Exploring Design Patterns: Singleton

Introduction

Hello developers! I'm back with my very inconsistent posting and I'm excited to announce this little series of articles on the topic of design patterns.

Since this is the first post in the series, I'll use it to explain a little bit about design patterns in general and then we'll move on to some concrete patterns.

Design patterns represent solutions to typical problems in software design. However, it's important to note that they are not FIXED solutions. They're a template that'll help you solve a particular design problem in your code. Even though they help solve common problems, each problem is always unique in its own way so you can't just "plug-in" the design pattern and expect it to magically work. They have to be modified and molded to fix your specific problem.

Other than that, they're useful as a common language that'll help you and your team communicate easier.

I'd like to keep the articles in this series in the range of 4-8 minute read time, so I won't be going too in depth about the topics. At the end of each article you can find the literature I use as well as a YouTube video explaining the pattern in code.

Singleton

The Singleton design pattern is one of, if not the most used design pattern. It’s useful when you need only one instance of a class and you need it to be accessible globally within the application. Why only one instance? Well, because you don’t need more. One instance would be useful for when you need a class to communicate with an external resource, for example a shared printer in an office. Another example where one instance is all that’s needed is a logger, why would you need more than one logger?

Formal definition: “The Singleton pattern ensures a class has only one instance and provides a global access point”.

Best uses are: logger, caches, registry settings, accessing external resources.

Now you’re probably thinking “hang on, this sounds a lot like just creating a global static variable of the class we need” and you wouldn’t be wrong, however there’s one catch. If you declare a global static variable, it will always be instantiated when you run the application. In small applications this isn't a big deal, but nothing in small applications is a big deal, so think bigger. What if we had 100 of those variables and they all get instantiated on start up. Some of them might be quite heavy and take a toll on our resources. The Singleton fixes this problem by having the power to apply a principle known as Lazy Loading (or Lazy Initialization). This term basically means that the variable gets initialized only when we explicitly request it for the first time.

So far everything sounds great, however for every design pattern there are consequences to its use. What’s the problem here? Well, let’s look back on the definition of the Singleton: “...provides a global access point”. By nature, any class that’s transformed into a singleton is not thread safe. The way around this problem is either by synchronizing the access to the initialization of the singleton variable or eagerly initializing it.

There's another problem with the Singleton, it doesn’t work well with inheritance. Also it’s tightly coupled to dependencies, it hides them and anyone using the Singleton will have to inspect it internally to find out what’s really going on. There is also the risk of memory leaks since it can hold the resource for an infinite amount of time.

There are also many problems with unit testing a Singleton. If you're running multiple unit tests that access the same Singleton, the Singleton will retain state between unit tests. This may lead to undesired results! The solution is to get access to the private static instance variable. Then set it to null at the end of each test.

Summary:

  • It ensures only one instance and global accessibility to an object
  • The main consequences are: thread safety, inheritance issues, hides dependencies, unit testing

Literature

If you want to learn more I highly recommend the book: Head First Design Patterns. It's an amazing and very understandable approach to explaining patterns and design principles.

I also recommend the following website: refactoring-guru and make sure to check out this very good YouTube video explaining the Singleton pattern in practice.

Thank you for your time ❤️. If you have any questions or suggestions, leave a comment down below.