Using Variable of AppDelegate as a Global Variable

2020-05-24 10:24发布

问题:

I have created a Variable called "myDBManager" in my AppDelegate:

@interface myAppDelegate : NSObject <UIApplicationDelegate> {
   MyDBManager *myDBManager;
}
@property (nonatomic, retain)  MyDBManager *myDBManager;

@end

which I use in most other classes as a global Variable holding all my critical application data. It gets only created once and dies at the end only. So for example to get to the myDBManager in AnyOtherClass

@interface AnyOtherClass :  UITableViewController {
   MyDBManager *myDBManager;
   NSObject *otherVar;
}
@property (nonatomic,retain)   MyDBManager *myDBManager;
@property (nonatomic,retain)   NSObject *otherVar;
@end

//getting the data from "global" myDBManager and putting it into local var of AnyOtherClass
- (void)viewWillAppear:(BOOL)animated {
   //get the myDBManager global Object
   MyAppDelegate *mainDelegate = (MyAppDelegate *)[[UIApplication sharedApplication]delegate];
   myDBManager = mainDelegate.myDBManager;
   }


-  (void)dealloc {
       [otherVar release];
        //[dancesDBManager release]; DO NOT RELEASE THIS SINCE ITS USED AS A GLOBAL VARIABLE!
        [super dealloc];
        }

Here is my question: while all other local variables of AnyOtherClass, such as "otherVar" have to be released in the dealloc method of AnyOtherClass (always- is that right?), releasing myDBManager within AnyOtherClass leads to errors in the app.

So I NEVER release the local myDBManager variable in any Class of my app - all other local variables are always released - and it works fine. (Even checking the retainCount).

Am I right, that ALL local variables of classes need to be released in the dealloc of that class, or is it actually OK, not to release these variables at all in cases of using a global variable construct as described? (or any other cases?)

Thanks very much for your help!

回答1:

In your scenario myDBManager is not a global or a local variable, it's an auto-retained property (marked with retain). According to The Objective-C Programming Language: Declared Properties, nonatomic,retain properties should be explicitly released in dealloc. However, if your property is synthesized, you don't have access to the backing member variable, thus you can't call release on it; you have to use the property setter to set it to nil, which will send release to the previous value. Are you by any chance setting the myDBManager property in AnyOtherClass and myAppDelegate to nil?

Update: @Don's answer is actually correct. You are not invoking the property setter (self.myDBManager), so the auto-retain does not kick in. I'll leave my answer so people can learn from my mistake. :-)



回答2:

You haven't retained it when you reference it in AnyOtherClass, so it is not yours to release at that point. You are setting the ivar directly, so the retain on the property does not come into play. If you called

self.myDBManager = mainDelegate.myDBManager;

you would be retaining it and would have to release it when you dealloc the class.

But, if it is a global variable, why not use it that way in AnyOtherClass? Why not call mainDelegate.myDBManager when you need the DB manager?