xcode 使用 AppDelegate 的变量作为全局变量 - 关于发布/保留的问题

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/3208371/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-14 19:31:27  来源:igfitidea点击:

Using Variable of AppDelegate as a Global Variable - question regarding release/retain

xcodeglobal-variablesrelease

提问by user387184

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

我在 AppDelegate 中创建了一个名为“myDBManager”的变量:

@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

我在大多数其他类中将其用作保存所有关键应用程序数据的全局变量。它只会创建一次,并且只会在最后死亡。例如,在 AnyOtherClass 中访问 myDBManager

@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.

这是我的问题:虽然必须在 AnyOtherClass 的 dealloc 方法中释放 AnyOtherClass 的所有其他局部变量,例如“otherVar”(总是 - 是吗?),但在 AnyOtherClass 中释放 myDBManager 会导致应用程序出错。

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).

所以我从来没有在我的应用程序的任何类中释放本地 myDBManager 变量 - 所有其他本地变量总是被释放 - 它工作正常。(甚至检查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?)

我是对的,类的所有局部变量都需要在该类的 dealloc 中释放,还是实际上可以,在使用所述全局变量构造的情况下根本不释放这些变量?(或任何其他情况?)

Thanks very much for your help!

非常感谢您的帮助!

采纳答案by Franci Penov

In your scenario myDBManageris 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,retainproperties 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 releaseon it; you have to use the property setter to set it to nil, which will send releaseto the previous value. Are you by any chance setting the myDBManagerproperty in AnyOtherClassand myAppDelegateto nil?

在您的场景中,myDBManager它不是全局变量或局部变量,而是自动保留的属性(标有retain)。根据The Objective-C Programming Language: Declared Propertiesnonatomic,retain属性应该在dealloc. 但是,如果您的属性是合成的,则您无权访问支持成员变量,因此您无法调用release它;您必须使用属性设置器将其设置为nil,这将发送release到以前的值。你任何机会设置myDBManager财产AnyOtherClassmyAppDelegatenil

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. :-)

更新:@Don 的回答实际上是正确的。您没有调用属性设置器 ( self.myDBManager),因此自动保留不会启动。我会留下我的答案,以便人们可以从我的错误中吸取教训。:-)

回答by Don

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

当您在 AnyOtherClass 中引用它时,您还没有保留它,因此此时您不能释放它。您正在直接设置 ivar,因此属性上的保留不会起作用。如果你打电话

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.myDBManagerwhen you need the DB manager?

但是,如果它是一个全局变量,为什么不在 AnyOtherClass 中那样使用它呢?mainDelegate.myDBManager当你需要数据库管理器时为什么不打电话?