Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Alternative to Singleton in Objective-C for better application design

It seems a lot of Objective-C code is using Singleton nowadays.

While a lot of people complaining about Singleton, e.g. Google (Where Have All the Singletons Gone?), their fellow engineers also use it anyway: http://code.google.com/mobile/analytics/docs/iphone/

I know we had some answers in Stack Overflow already but they are not totally specific to Objective-C as a dynamic language: Objective C has categories, while many other languages do not.

So what is your opinion? Do you still use Singleton? If so, how do you make your app more testable?

Updated: I think we need to use codes as example for more concrete discussion, so much discussions on SO are theory based without a single line of code

Let's use the Google Analytics iOS SDK as an example:

// Initialization
[[GANTracker sharedTracker] startTrackerWithAccountID:@"UA-0000000-1"
                                        dispatchPeriod:kGANDispatchPeriodSec
                                              delegate:nil];
// Track page view
[[GANTracker sharedTracker] trackPageview:@"/app_entry_point"
                                   withError:&error];

The beauty of the above code is once you have initialized using the method "startTrackerWithAccountID", you can run method "trackPageview" throughout out your apps without passing through configurations.

If you think Singleton is bad, can you improve the above code?

Much thanked for your input, have a happy Friday.

like image 475
Howard Avatar asked May 06 '11 14:05

Howard


People also ask

Which of the following is an alternative for a singleton in?

Better Alternative of Singleton Pattern So, you can see that Dependency Injection offers a better alternative to Singleton Pattern in Java.

Why should you avoid singletons?

By using singletons in your project, you start to create technical debt. Singletons tend to spread like a virus because it's so easy to access them. It's difficult to keep track of where they're used and getting rid of a singleton can be a refactoring nightmare in large or complex projects.

What is singleton class in Objective C?

What is a Singleton Class? A singleton class returns the same instance no matter how many times an application requests it. Unlike a regular class, A singleton object provides a global point of access to the resources of its class.


2 Answers

I think most developers go through the Singleton phase, where you have everything you need at your fingertips, in a bunch of wonderful Singletons.

Then you discover that unit testing with Singletons can be difficult. You don't actually want to connect to the database, but your Singleton does. Add a layer of redirection and mock it.

Then you discover that unit testing isn't the only time you need different behaviour. You make your Singleton configurable to have different behaviour based on a parameter. You start to wonder if you need to split it into two Singletons. Then your code needs to know which Singleton to use, so you need a Singleton that knows which Singleton to use.

Then some other code starts messing with the values in your Singleton, while you're using it. How dare they! If you wanted just anybody to get at those values from anywhere, you'd make them global...

Once you get to this point, you start wondering if Singletons were the right solution. You start to see the dangers of global data, particularly within an OO design, where you just assume your data won't get poked at by other people.

So you go back and start passing the data along, rather than looking it up (this used to be called good OO design, but now it has a fancy name like "Dependency Injection").

Eventually you learn that Singletons are fine in moderation. You learn to recognize when your Singleton needs to stop being single.

So you get shared objects like UIApplication and NSUserDefaults. Those are good uses of Singletons.

I got burned enough in the Java Singleton craze a decade ago. I don't even consider writing my own Singletons. The only time I've needed anything similar in recent memory is wanting to cache the result of [NSCalendar currentCalendar] (which takes a long time). I created a category on NSCalendar and cached it as a static variable. I felt a bit dirty, but the alternative was painfully slow code.

To summarize and for those who tl;dr:

Singletons are a tool. They're not likely to be the right tool, but you have to discover that for yourself.

like image 39
Terry Wilcox Avatar answered Sep 22 '22 23:09

Terry Wilcox


This post is likely to be downvote-bait, but I don't really understand why singletons get no love. They're perfectly valid, you just have to understand what they're useful for.

In iOS development, you have one and only one instance of the application you currently are. You're only one application, right? You're not two or zero applications, are you? So the framework provides you with a UIApplication singleton through which to get at application-level os and framework features. It models something appropriately to have that be a singleton.

If you've got data fields of which there can and should be only one, and you need to get to them from all over the place in your app, there's totally nothing wrong with modeling that as a singleton too. Creating a singleton as a globals bucket is probably a misuse of the pattern, and I think that's probably what most people object to about them. But if you're modeling something that has "singleness" to it, a singleton might well be the way to go.

Some developers seem to have a fundamental disgust for singletons, but when actually asked why, they mumble something about globals and namespaces and aesthetics. Which I guess I can understand, if you've really resolved once and for all that Singletons are an anti-pattern and to be abhorred in all cases. But you're not thinking anymore, at that point. And the framework design disagrees with you.

like image 100
Dan Ray Avatar answered Sep 19 '22 23:09

Dan Ray