由于推送和弹出 UIViewControllers,UINavigationController 崩溃 [英] UINavigationController crash because of pushing and poping UIViewControllers

查看:13
本文介绍了由于推送和弹出 UIViewControllers,UINavigationController 崩溃的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

问题:我有一个 UINavigationController 作为 UIWindow 的子视图、一个 rootViewController 类和一个自定义 MyViewController 类.以下步骤将获得 Exc_Bad_Access,100% 可重现.

The issue: I have a UINavigationController as as subview of UIWindow, a rootViewController class and a custom MyViewController class. The following steps will get a Exc_Bad_Access, 100% reproducible.:

[myNaviationController pushViewController:myViewController_1stInstance animated:YES];
[myNaviationController pushViewController:myViewController_2ndInstance animated:YES];

点击左后的 tapBarItem 两次(弹出两个 myViewController 实例)以显示 rootViewController.

Hit the left back tapBarItem twice (pop out two of the myViewController instances) to show the rootViewController.

经过 1/2 天的痛苦尝试和错误,我终于找到了答案,但也提出了一个问题.

After a painful 1/2 day of try and error, I finally figure out the answer but also raise a question.

解决方案:我在 .m 文件中声明了许多对象,作为声明私有变量的一种惰性方式,以避免弄乱 .h 文件.例如,

The Solution: I declared many objects in the .m file as a lazy way of declaring private variables to avoid cluttering the .h file. For instance,

#impoart "MyViewController.h"
NSMutableString*variable1;

@implement ...

-(id)init
{
   ...
   varialbe1=[[NSMutableString alloc] init];
   ...
}

-(void)dealloc
{
   [variable1 release];
}

由于某些原因,当加载 myViewController_2ndInstance 的视图后卸载 myViewController_1stInstance 的视图(但仍在导航控制器的堆栈中)时,iphone OS 可能会丢失这些惰性私有"变量内存分配的跟踪.由于 myViewController_2ndInstance'view 仍然加载,第一次点击后面的 tapBarItem 是可以的.但是第二次点击后面的 tapBarItem 给了我地狱,因为它试图释放第一个实例.它称为 [variable release] 导致 Exc_Bad_Access 因为它随机指向(松散的指针).

For some reasons, the iphone OS may loose track of these "lazy private" variables memory allocation when myViewController_1stInstance's view is unloaded (but still in the navigation controller's stacks) after loading the view of myViewController_2ndInstance. The first time to tap the back tapBarItem is ok since myViewController_2ndInstance'view is still loaded. But the 2nd tap on the back tapBarItem gave me hell because it tried to dealloc the 1st instance. It called [variable release] resulted in Exc_Bad_Access because it pointed randomly (loose pointer).

要解决这个问题很简单,在 .h 文件中将 variable1 声明为 @private.

To fix this problem is simple, declare variable1 as a @private in the .h file.

这是我的问题:在涉及 UINavigationController 之前,我一直在使用惰性私有"变量很长一段时间没有任何问题.这是 iPhone OS 中的错误吗?还是我对 Objective C 存在根本性的误解?

Here is my Question: I have been using the "lazy private" variables for quite some time without any issues until they are involved in UINavigationController. Is this a bug in iPhone OS? Or there is a fundamental misunderstanding on my part about Objective C?

推荐答案

这可能与使用相同静态分配变量的视图控制器的两个实例有关.

It might be related to both instances of your view controller using the same statically-allocated variable.

换句话说,myViewController_1stInstancemyViewController_2ndInstance 都在内存中使用相同的 variable1 位置并相互覆盖.

In other words, both myViewController_1stInstance and myViewController_2ndInstance are using the same variable1 location in memory and overwriting one another.

在你的 @interface 定义之后在花括号内声明的变量有一个由运行时为类的每个实例分配的内存位置(每次你调用 [alloc].在全局范围内(即在任何函数或类声明之外)声明的变量就是:全局的.这意味着该变量在每个运行的应用程序副本中只能保存一个值.

Variables declared inside of the curly braces after your @interface definition have a memory location allocated by the runtime for each instance of the class (every time you call [<ClassName> alloc]. Variables declared in the global scope (that is, outside of any functions or class declarations) are just that: global. That means that the variable can only hold one value per running copy of your application.

Objective-C 中没有真正的私有变量,但您可以在编译时将它们隐藏在其他实例中,如 这里.

There are no truly private variables in Objective-C, but you can hide them from other instances at compile time as described here.

这篇关于由于推送和弹出 UIViewControllers,UINavigationController 崩溃的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆