I checked those links and the problems mentioned seem to be generally linked to wrong assumptions about restrictions of a singleton. Any singleton is easily testable (as opposed to static classes) and if you need to synchronize getters you should probably not be using a singleton in that place. the 'Singleton' pattern is also not limited to some getInstance() method at all. But in a case where you need to concurrently change state of an object often, using a singleton is of course not a good idea. This doesn't mean a Singleton is evil, it just means it is used in the wrong place often.. Probably because it is (one of) the most famous patterns. Imagine if everyone would be using facades to be doing fine grained method calls and making transfer objects with the same properties as their entities. Doesn't mean these patterns are evil, it just means you're not doing it right.
My top 5 overused patterns:
Singletons are not easily testable. You can not create mock objects of them, there's no point in injecting them, and furthermore, your tests can not guarantee that they are in a valid state if they're not immutable.
What I don't understand is *why* people want to make their classes instance controlled. For non-essential features like Logging I understand, but business logic? Never. Just create the right amount of instances and inject them.
Dieter, I think you misunderstood. Its not about Singleton is bad but many times this has been used as a shortcut so that the designer doesn't need to think correctly about object visibility.
Joined: Aug 06, 2010
I disagree. Testability of a singleton is completely dependent on the implementation. A Singleton's factory method is not necessarily implemented inside the singleton itself, and a singleton not necessarily prohibits inheritance.
Of course, the easiest example is using singleton injection in Spring. The class is just a POJO, testable and extensible, but it becomes a singleton only because the injection will always inject the same instance.
I will give a concrete example from a former project:
We had a certain huge XML sitemap file which was being read all through the application, which was causing numerous problems with performance, resource locking and uniformity. Noticing this while profiling, I decided to do a small test containing a change listener for the file, a builder that created a sitemap object hierarchy with all the relevant data loaded into memory, and implemented a provider object for the sitemap object. This was in the spring context, and would return the currently up-to-date sitemap object for any 'getSitemapInstance()' call.
After using this in all the instances that the XML file was used before, the performance of the application had increased factor 30.
So is your problem with this Singleton, that this is technically not a Singleton? Because it is, functionally...
Spring's singleton is not a Singleton. In a Singleton pattern, there can be only one instance of the given class. Spring calls it singleton, but it's not an implementation of the Singleton pattern.
Joined: Aug 06, 2010
I guess I disagree on that idea, simply because dependency injection is a solution for possible technical shortcomings of a singleton, but not the possible functional shortcomings.
To me, a pattern is never about technical implementation, but the idea behind. The idea behind a singleton is a class that only has one meaningful object in a certain application. The spring singleton in my example was the provider class, but that is a meaningless holder. The real singleton was the Sitemap class. And though it is just a POJO that can be instantiated by anyone, there is no other meaningful implementation of it possible in the application. That means in my opinion that it's a singleton.
After some googling for definitions of a singleton, along with running into the forced code implementations, I came up with two partial definitions:
"the singleton class has control over how it is created"
"there is only one singleton in a JVM"
In my example, it is the listener that has control over when it is created, the builder that controls how it is created. There is only ever one Sitemap instance linked to the provider, and the provider must be used to reach the sitemap. Any Provider instance instantiated by the developer will not contain a sitemap object. Thus the object is very much unique and -indirectly- has full control over its instantiation - that is, the developer does not govern the instantiation of the object. That makes it a singleton functionally - on a component level - though it is not a singleton implementation in the technical sense.
So I guess whether you can call it a Singleton object is completely dependent on your perception of what a singleton object actually is. Me, I tend not to restrict a pattern to any particular implementation, whether it be a static method or an enumeration type. If I shouldn't be using 'Singleton' for this pattern, maybe you're right. In that case, I guess there are many common patterns I say I'm using, but am not really using
When people talk about Singleton pattern, they talk about Singleton pattern the way GoF defined it, and GoF has a very precise definition of every pattern in the book. We all had this big meeting and we decided that GoF's definition of Singleton is the only definition of Singleton, and GoF's Singleton sucks. Didn't you get the memo? Seriously speaking, when people are talking about any pattern, the convention is to consider GoF Design pattern book to be the dictionary of design patterns. It doesn't matter what your definition of a pattern is. As a convinience, the industry has decided to use GoF's book as the dictionary.
Spring's implementation of singleton objects doesn't fit the SIngleton pattern as defined in the book. That doesn't mean that Spring's implementation is not useful. It just means that it's not a Singleton.