gpt4 book ai didi

ios - Popover Controller 在 iOS 8 中被销毁(nil)

转载 作者:行者123 更新时间:2023-12-01 18:54:38 24 4
gpt4 key购买 nike

在 iOS 7 中,我曾经在 View Controller 中定义对弹出框 Controller 的弱引用(显示在弹出框中)。我使用这个对 popover Controller 的引用来以编程方式关闭 popover。另外,我定义了 popover Controller 的委托(delegate)以跟踪解除事件(popoverControllerShouldDismissPopover 等)。

在 iOS 8 中它停止工作。调查显示弱引用指向nil过了一段时间。委托(delegate)也停止工作(据我所知,这是因为委托(delegate)是在弹出 Controller 中定义的,在弹出窗口显示后由于某种原因在 iOS 8 中被销毁)。

通过将属性更改为 strong 解决了问题引用。
对于一些弹出框(我有一堆),我必须添加强引用只是为了保持 popoverController 活着,因为我需要 delegate去工作。这是明显的黑客行为。我添加了我不需要也不需要使用的属性。

您能否澄清一下这是否是正确的方法。我担心的是强引用可能会导致内存泄漏。我也不太明白为什么 popoverController 在 iOS 8 中被销毁,而 popover 仍在屏幕上。

这是我的具有弱属性的 View Controller 。更改后weakstrong在 iOS 8 下开始正常工作:

@interface TFDSuggestionViewController : UIViewController
...
@property (weak, nonatomic) UIPopoverController *myPopoverController;
...
@end

这就是我为我的属性(property)分配值(value)并在 prepareForSegue 中委托(delegate)的方式调用 View Controller 的方法:
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
if ([segue.identifier isEqualToString:@"suggestions"]) {
TFDSuggestionViewController *suggController = ((TFDSuggestionViewController *)[segue destinationViewController]);
suggController.myPopoverController = ((UIStoryboardPopoverSegue *)segue).popoverController;
((UIStoryboardPopoverSegue *)segue).popoverController.delegate = self;
}
}

谢谢你的建议!

最佳答案

在过去的手动内存管理中,有一种叫做引用计数的东西。它本质上是一个对象被其他对象或应用程序保留(强引用)的次数。在最近的 ARC(自动引用计数)中,我们不再需要 [object retain][object release] .这些 Action 由编译器为我们处理。

现在到你的情况。弱引用不会增加您正在引用的对象的引用计数。所以如果你在一个范围内创建一个对象,给它分配一个弱引用,然后离开这个范围,你的对象的引用计数是 0。

-(void)SomeMethod
{
ClassObject *object = [[ClassObject alloc] init];
//object's internal reference count is now 1

self.myPopoverController = object;
//Since myPopoverController is a weak reference, object still has reference count of 1

//Some other code that does things and stuff.
}
//We just closed the scope, so object's reference count is now 0
//ARC is free to release the object to free it's memory, causing any
//weak references to return nil

在上面的示例中,它显示了一个非常简单的对象生命周期。一旦你了解了生命周期,你就会明白为什么在这种情况下弱引用对你毫无用处。

至于为什么它在 iOS7 而不是在 iOS8 中工作,我唯一的答案是 iOS8 在垃圾收集方面可能效率更高。如果您在 iOS7 中运行它一百万次,我相信您至少会找到一个发生完全相同问题的示例。这是新操作系统更加普遍的代码缺陷。

如果您希望对象保持事件状态,您需要至少有一个对其的强引用。唯一的预防措施是,当您调用驳回时,您应该 nil 强引用。那么应该没有不利的内存问题需要解决。

还有一点非常重要。 UIPopoverController与屏幕上可见的对象不同。屏幕上可见的是 UIPopoverController.view . View 仍然由 View 层次结构保留,但 Controller 需要由您保留,以免它被释放。一旦 UIPopoverController发布后, View 的委托(delegate)将为零,因为 view.delegate也是弱引用。

研究对象生命周期。它将帮助您避免将来随着操作系统在内存处理方面变得越来越高效而肯定会出现的垃圾收集问题。

关于ios - Popover Controller 在 iOS 8 中被销毁(nil),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28503571/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com