Global Variables in iPhone Objective-C

If you studied any programming in school you were probably told to never use global variables because ultimately it can cause you end up with a messy slob of code that is difficult to maintain, and this holds true in iPhone Objective-C.

While that is correct, the truth of the matter is there are many situations when you want to have a global variable, as often there are variables that don’t really belong to any objects, and you want to change them from many locations within your application.  You could of course place variables in your AppDelegate and access them through there, but this is not a good solution and can turn things into a great big mess which is the reason why many college professors forbid the use of global variables in all languages (not simply because they may have never actually coded anything).  The solution to this is to create a class using the Singleton design pattern.  For example:

@interface VariableStore : NSObject
{
    // Place any "global" variables here
}
// message from which our instance is obtained
+ (VariableStore *)sharedInstance;
@end

@implementation VariableStore
+ (VariableStore *)sharedInstance
{
    // the instance of this class is stored here
    static VariableStore *myInstance = nil;
 
    // check to see if an instance already exists
    if (nil == myInstance) {
        myInstance  = [[[self class] alloc] init];
        // initialize variables here
    }
    // return the instance of this class
    return myInstance;
}
@end

Whenever you need to access a variable assuming you have a getter defined as the variable name simply use:

[[VariableStore sharedInstance] variableName]

If the variable is a primitive, and a global constant then there is really no need to use a singleton as above you can use a preprocessor #define statement. For example:

#define VARIABLE value

Now when you need to share a variable between many objects this should make for much simpler, and cleaner code.

If you’re transitioning to Objective-C from C/C++/Java you might want to check out my Objective-C Cheat Sheet.

DeliciousTwitterTechnoratiFacebookLinkedInEmail
Tags: , , , , ,

Submit A Resource

Have you created a useful tutorial, library or tool for iOS development that you would like to get in front of our 300,000+ monthly page views from iOS developers?

You can send a Tweet to @maniacdev on Twitter or submit the url here.

The resources we feel will appeal to our readers the most will be posted on the front page.

  • jzting

    thanks for this!

  • Brian

    I'm new to iPhone / objective c. I would ask, if these are global, do you need to make accessors and setters thread safe? Or are most apps single threaded unless/until you explicitly start another thread? Is the iPhone even multithreaded?

    Also, you could define class methods as getter and setter methods, but then you are doing twice the work. Although I did read that an instance (a class as well,perhaps) can get a message and pass it along to another object to process it. If you could do this for all messages not implemented, just send all unhandled messages sent to the class over to the instance… Something to think about…

  • http://maniacdev.com maniacdev

    Hi Brian,

    there are no real “global” variables in Objective-c, the purpose of the singleton in this case is so that we can access it from anywhere, and access the variables in there, the getters and setters are made in the singleton class's property statements. You can set the properties to be atomic and the getters/setters created will be thread safe.

  • bcao

    I still get duplicate symbol error during build for the singleton class name, VariableStore, when include the same header file with globals in multiple files. Any way to resolve that? Thanks,

  • Sean

    I'm having trouble accessing the variable after doing this. I get a few warnings:
    – “VariableStore may not respond to variableName (messages without a matching method signature will be assumed to return id and accept '…' as arguments)
    – initialization makes integer from pointer without a cast

    Are there some steps missing from the post? I'm trying to get a handle on the singleton concept.

    Thanks,
    Sean

  • Zheng

    Nice, thanks for sharing this

  • Charles

    Thanks so much for this tip. I've been trying for a while to get the singleton to work.

  • Charles

    Thanks so much for this tip. I've been trying for a while to get the singleton to work.

  • nico

    i have searched for a solution like this, but – maybe i interpreted it wrong – i don’t get the initialization at // initialize variables here to work
    in the .m i have made this:

    @implementation VariableStore
    //synthesize [3]
    @synthesize globalerstring;

    + (VariableStore *)sharedInstance
    {….

    in the .h
    #import

    @interface VariableStore : NSObject
    {
    // Place any “global” variables here [1]
    NSString *globalerstring;

    }
    // message from which our instance is obtained
    + (VariableStore *)sharedInstance;

    //properties [2]

    @property (nonatomic,retain) NSString *globalerstring;

    @end

    maybe i haven’t understood the principle in the right way. could anybody do one example for any variable ?

  • nico

    i have searched for a solution like this, but – maybe i interpreted it wrong – i don’t get the initialization at // initialize variables here to work
    in the .m i have made this:

    @implementation VariableStore
    //synthesize [3]
    @synthesize globalerstring;

    + (VariableStore *)sharedInstance
    {….

    in the .h
    #import

    @interface VariableStore : NSObject
    {
    // Place any “global” variables here [1]
    NSString *globalerstring;

    }
    // message from which our instance is obtained
    + (VariableStore *)sharedInstance;

    //properties [2]

    @property (nonatomic,retain) NSString *globalerstring;

    @end

    maybe i haven’t understood the principle in the right way. could anybody do one example for any variable ?

  • nico

    i have searched for a solution like this, but – maybe i interpreted it wrong – i don’t get the initialization at // initialize variables here to work
    in the .m i have made this:

    @implementation VariableStore
    //synthesize [3]
    @synthesize globalerstring;

    + (VariableStore *)sharedInstance
    {….

    in the .h
    #import

    @interface VariableStore : NSObject
    {
    // Place any “global” variables here [1]
    NSString *globalerstring;

    }
    // message from which our instance is obtained
    + (VariableStore *)sharedInstance;

    //properties [2]

    @property (nonatomic,retain) NSString *globalerstring;

    @end

    maybe i haven’t understood the principle in the right way. could anybody do one example for any variable ?

  • nico

    btw: who is the thief ?
    http://www.picksourcecode.com/ps/ct/161183.php

    (@mod: you dont have to make this post public)

  • nico

    btw: who is the thief ?
    http://www.picksourcecode.com/ps/ct/161183.php

    (@mod: you dont have to make this post public)

  • nico

    btw: who is the thief ?
    http://www.picksourcecode.com/ps/ct/161183.php

    (@mod: you dont have to make this post public)

  • John

    That post came out several months after mine so clearly they just copied. Thanks for pointing that out.

  • John

    That post came out several months after mine so clearly they just copied. Thanks for pointing that out.

  • John

    That post came out several months after mine so clearly they just copied. Thanks for pointing that out.

  • Daniel

    Hi, I’m having the same problem as Sean:
    – “VariableStore may not respond to variableName (messages without a matching method signature will be assumed to return id and accept ‘…’ as arguments)

    I’m clearly missing some step, but which one?

    Thanks
    Daniel

  • Daniel

    Hi, I’m having the same problem as Sean:
    – “VariableStore may not respond to variableName (messages without a matching method signature will be assumed to return id and accept ‘…’ as arguments)

    I’m clearly missing some step, but which one?

    Thanks
    Daniel

  • Daniel

    Hi, I’m having the same problem as Sean:
    – “VariableStore may not respond to variableName (messages without a matching method signature will be assumed to return id and accept ‘…’ as arguments)

    I’m clearly missing some step, but which one?

    Thanks
    Daniel

  • Petrus Ali Saputra

    Hi, I’m pretty new with Obj C. Every class that I know, always have dealloc method. Should I put dealloc in this Singleton? Thanks.

  • Petrus Ali Saputra

    Hi, I’m pretty new with Obj C. Every class that I know, always have dealloc method. Should I put dealloc in this Singleton? Thanks.

  • Petrus Ali Saputra

    Hi, I’m pretty new with Obj C. Every class that I know, always have dealloc method. Should I put dealloc in this Singleton? Thanks.

  • dpmguise

    Great stuff, concise and simple.

  • dpmguise

    Great stuff, concise and simple.

  • dpmguise

    Great stuff, concise and simple.

  • Frank

    I make use of 4 global variable parameters. Input once and used throughout three view controllers. Never modified. I tried to use your singleton and sought advice from Stack Overflow on how best to get four UITextfields (the parameters) into the singleton variables. I came in for some criticism for a) using a singleton for such a piffling requirement and b) for not complying with the Apple recommended Design Pattern for a singleton. Can’t win. Don’t use Globals and don’t use Singletons for program-wide use.

    I ended up using 4 Globals and haven’t looked back. So, when is it correct/incorrect to use a singleton?

  • Frank

    I make use of 4 global variable parameters. Input once and used throughout three view controllers. Never modified. I tried to use your singleton and sought advice from Stack Overflow on how best to get four UITextfields (the parameters) into the singleton variables. I came in for some criticism for a) using a singleton for such a piffling requirement and b) for not complying with the Apple recommended Design Pattern for a singleton. Can’t win. Don’t use Globals and don’t use Singletons for program-wide use.

    I ended up using 4 Globals and haven’t looked back. So, when is it correct/incorrect to use a singleton?

  • Frank

    I make use of 4 global variable parameters. Input once and used throughout three view controllers. Never modified. I tried to use your singleton and sought advice from Stack Overflow on how best to get four UITextfields (the parameters) into the singleton variables. I came in for some criticism for a) using a singleton for such a piffling requirement and b) for not complying with the Apple recommended Design Pattern for a singleton. Can’t win. Don’t use Globals and don’t use Singletons for program-wide use.

    I ended up using 4 Globals and haven’t looked back. So, when is it correct/incorrect to use a singleton?

  • Chu

    Hi
    Really thanks it works and better than my F…ing global … Thks a lot

  • kPK

    Pretty good stuff ! Works like charm !!
    Thanks

  • bjorn

    In the header you need to add something like:
    @propery(nonatomic) variabletype variable;

    You also need this is implementation file:
    @synthesize variable;

    If not, you will get “VariableStore may not respond to variableName”.

  • josevin

    thank you….i am searching for this…….

  • Severson

    wait… won’t it re-allocate and re-initiate the class every time you call the “sharedInstance” method, thus giving you a blank slate every time you want to use your variable. yeah I’m confused.

  • Severson

    shouldn’t the “static ClassName *myInstance = nil” be outside of the Global method?? Else, you’d have “myInstance” be nil every time you call it, thus always allocating and initializing the class every time you call the method. 

    idk, maybe I’m missing something.

  • http://maniacdev.com maniacdev

    Nope. it will only instantiate if myInstance is nil.

  • http://maniacdev.com maniacdev

    nope.. it’s a static variable so it will not be allocated and initialized every time you call the method.

  • Nelson Rodrigues

    Do we need to release the global variables? Thanks!