To get a good idea of what this article will take on, it is important to know the basis of what the Singleton Design Pattern really does. Let's imagine we are building an app for playing scrabble. You need to give every player the letters and they cannot be more than what the data set provided has in stock. There is, however, one rule in this scrabble game, that there can never be the same sample of letters given out to a player if another has the exact same sample of letters.
The image above shows the basic concept of what the game should entail in the Singleton language. There are a few places to focus on. The main one is that you are trying to give the players (instance) one set of letters (Client set A, B, C). It is key to also remember that each player can only have one set of letters and that they cannot be the same set that other players have.
This previous image shows the process which the Singleton program will take, starting with the Word Set (client) it will run redundancies to make sure that every set of letters is unique and that each player or instance gets only one class or set of letters.You can also use dependency injection to make everything more clear and easier to maintain. Check out how dependency injection works in another Mäd article here.
What is Singleton?
Singleton is a design pattern for any programming language. Singleton is a fairly simple and easy design pattern to understand and learn. The Singleton pattern guarantees that only one instance of a class is instantiated. If you've worked with Apple's frameworks, then chances are that you've already used the Singleton pattern. Take a look at these examples. They probably look familiar.
How to implement Singleton Creating a Singleton pattern is easy peasy.
Step 1: You have to create a class because Singleton is a reference type.
Step 2: You just have to create an instance of the class which declares as a static constant.
Step 3: Last but not least, make the initializer private to prevent creating other instances of Singleton and declare any variable you need to use.
Note: Keep in mind that while Apple recommends that we should prefer value types to reference types, there are still plenty of examples, such as the Singleton pattern, where a reference type is needed. When we continuously tell ourselves to prefer value types to reference types, it can be very easy to forget that there are times where a reference type is needed. Don't forget to use reference types with this pattern as needed.
Pros of Singleton
·Instance control: Singleton prevents other objects from instantiating their own copies of the Singleton object, ensuring that all objects access the single instance.
·Flexibility: Since the class controls the instantiation process, the class has the flexibility to change the instantiation process.
·Easy to implement: Easy to create and we could use it anywhere for the lifetime of the app The advantage of Singleton over global variables is that you are absolutely sure of the number of instances when you use Singleton. However, you can still change your mind and manage any number of instances. Having a very versatile design pattern that can work well for many different applications and processes.
Cons of Singleton
·They are a global mutable shared state. Their state is automatically shared across the entire app, and bugs can often start occurring when that state changes unexpectedly.
·The relationships between Singletons and the code that depends on them is usually not very well defined. Since Singletons are so convenient and easy to access — using them extensively usually leads to very hard to maintain “spaghetti code” that doesn’t have clear separations between objects.
·Managing their life-cycle can be tricky. Since Singletons are alive during the entire lifespan of an application, managing them can be really hard, and they usually have to rely on optionals to keep track of values. This also makes code that relies on Singletons really hard to test, since you can’t easily start from a “clean slate” in each test case.
The disadvantages of Singleton over a global mutable shared state can give you a real headache if the state changes unexpectedly and also keep your code tightly coupled. It will make difficult to test when your code is not loosely coupled so it will cause a lot problems to maintain.
Dependency Injection (Singleton problem solved)
Even if you decide to use Singleton in a project, that doesn't mean you have to access them anywhere or any time in your project.You can still use dependency injection to pass the Singleton object to the objects that need it. By adopting dependency injection to pass Singletons around, the interface of your class remains clear and transparent. In other words, the interface of the class describes its dependencies. This is very, very useful. It immediately shows which objects the class needs to perform its duties.
Finally, it is very important to understand how to create your Singleton class in your project. Knowing how to implement this pattern will allow you to take much less time to create your work. Yet Singleton does have It’s advantages and disadvantages as I mentioned previously. If you continue using the Singleton pattern inside your projects it can, in turn, become quite hard to manage the life-cycle of your Singleton class. As much as using Singleton is a great way to do simple and easy patterns, it is best to try and avoid the overuse of it. If you find yourself overusing Singleton, a simple way to avoid frustrations and the negative effects of this pattern would be to include the use of dependency injection. This would allow for a smoother work, which can be tested and maintained much easier than using Singleton.