将 UIViewController 设置为另一个 UIViewController 的属性是否一个坏主意?

Posted

技术标签:

【中文标题】将 UIViewController 设置为另一个 UIViewController 的属性是否一个坏主意?【英文标题】:Is it a bad idea to set a UIViewController as a property of another UIViewController?将 UIViewController 设置为另一个 UIViewController 的属性是不是一个坏主意? 【发布时间】:2011-06-30 14:14:00 【问题描述】:

例如,假设我有一个 RootViewController 类和 AnotherViewController 类,我需要将我的 RootViewController 中的属性从 AnotherViewController... AnotherViewController.h(这样我就可以访问它的实例变量)?

@interface AnotherViewController : UIViewController 
    RootViewController *rootViewController;


@property (nonatomic, retain) RootViewController *rootViewController;
@end

@implementation AnotherViewController

@synthesize rootViewController;

- (void)someMethod 
    // set the data was added flag, so the rootViewController knows to scroll to the bottom of the tableView to show the new data
    self.rootViewController.dataWasAdded = YES;

    // if the user came in via a search result, make the search controller's tableView go away
    self.rootViewController.searchDisplayController.active = NO;

如果这不是一个好主意,谁能解释为什么?

在上面的代码中,我知道我可以使用协议/委托来处理相同的事情 - 我猜我可能应该这样做。但是,我读过的书籍或其他材料都没有真正讨论过这个问题。

我问的原因是我正在使我的应用程序通用,并使用UISplitViewController 我注意到我需要经常更新我的“主视图”,因为用户在“细节视图”。因此,我采取了看似简单的方法并开始将UIViewControllers 设置为属性......但我遇到了一些难以跟踪的内存泄漏和偶尔的崩溃。我读了一些关于“循环引用”的文章,想知道这是否是问题的一部分(我确实有几个地方将UIViewControllers 设置为彼此的属性)。

感谢您提供任何见解或指向涵盖此内容的参考资料。

【问题讨论】:

【参考方案1】:

我会避免养成这种习惯,因为有更好更安全的选择。使用协议/委托是 Apple 跨类管理数据的首选方式。您还可以设置 NSNotifications 以将数据/事件从一个类发送/触发到另一个类。 Key Value Observing (KVO) 也是监听变化的好方法。

在 MVC 结构中,子视图和下游控制器真的不应该知道(也就是保留引用)它们的父视图。它应该始终与父母管理和跟踪孩子的方式相反。

【讨论】:

+1 说得好。父控制器保留对其子视图控制器的引用很好——那里已经存在依赖关系,因为父控制器通常必须实例化子视图。但是,如果您可以避免在另一个方向上的依赖关系,那么子控制器将更加独立、可重用且更易于测试。 感谢您的回复。听起来我需要重组我的一些代码。我在我的 4 个子视图控制器中以至少 17 种不同的方法访问父视图控制器,因此需要一些工作 - 但希望这将清除(或帮助我追踪)莫名其妙的内存泄漏。这样做还应该让我摆脱一些我必须放入接口头文件的#import指令(@class 不起作用)并摆脱潜在的循环依赖。

以上是关于将 UIViewController 设置为另一个 UIViewController 的属性是否一个坏主意?的主要内容,如果未能解决你的问题,请参考以下文章

如何将 UIView 框架自动调整为另一个 UIView 框架

使用自定义 segue 动画将一个视图替换为另一个视图?

切换单元格大小按钮不更改单元格标识符 UIViewController

将 UIViewController 的视图调整为父 UIWindow 的边界

适当调整 UIViewController 的视图大小

将颜色从光谱设置为另一个 div