MVC模式:Massive View Controller?
Posted dennis1012512
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了MVC模式:Massive View Controller?相关的知识,希望对你有一定的参考价值。
每一个新的ios开发者都必须立刻熟练掌握一大堆东西:新的语言,新的框架以及Apple推崇的设计模式:模型 - 视图 - 控制器(MVC模式)
尽快上手iOS开发是个令人畏惧的事,但其实更多的情况是开发者并没有没有花很多功夫在理解MVC模式上,而这也更让开发者在歧途上越走越远。
这篇文章能帮你避免app缺乏扩展性的问题,同时你将会学到如何正确使用MVC模式来构造你的app。这些最好实践建议都是来自于自己不断地练习和尝试。
希望看完这篇文章,你就会明白怎样在你的app中实践这种最优化的设计模式同时最大程度上避免出现让你头痛的结构性问题。
let's go!
MVC 101
提醒:如果你了解MVC的概念,可以直接跳过这一节到下一节来直接开始看如何实践。
从一个更高的层次来看,MVC正如它名字所示的一样由三部分组成:模型,视图和控制器。
模型是你储存数据的地方。很多东西像类,映射关系,网络层的代码等等都本放在这里。
视图层是你app的外观。它基本上是可重复使用的,因为这里并没有储存具体实现层面的内容。例如像
UILabel
就是一个在屏幕上展示文字的视图,可以很容易复用在其余地方。控制器处在模型和视图之间,一般都是靠代理模式来实现的。在理想的情况下,控制器不知道它所使用的视图的具体实现。相反的,它通过接口协议(protocol)来与视图进行交流。一个经典的例子是
UITableView
和它的数据源Data Source使用UITableViewDataSource
协议来进行交流。
当你把所有的东西放在一块,它看起来像这样:
很简单吧?
正如他们所说,魔鬼在细节里面。当你真正开始实践MVC时,事情就会变得非常棘手,你马上会看到的。
苹果的官方MVC文档解释了这些细节,可以给你一个非常理论的认识,能帮你避免一些可能的陷阱。
但是从实际的角度来看,这需要了解太多无关的东西。所以我们还是少谈理论直接上手吧!
从哪儿开始?
虽然理解MVC的理论很容易,但有时实践最初的时候很难一下搞懂从哪儿开始下手。我们花点时间来看看吧。
视图层 View Layer
当用户和你的app开始交互,他们实际是与视图层在进行交互。视图一般被当做你app中的“傻帽”,因为它并没有包含任何具体工作逻辑。从代码的角度,你将会在这一层看到这些东西:
UIView
的子类。他们来自最基础的UIView
并可以通过自己的定制来不断复杂。一个
UIViewController
(有争议)。因为UIViewController和它自己的根UIView紧密联系在一起和它自己的生命周期(lifecycle),我个人认为它属于视图层,但不是每个人都同意。动画和
UIViewController
的过渡UIKit/Appkit, Core Animation 和 Core Graphics中的类
典型的代码异味(Smell Code)在这一层有很大的栖息空间,那些与UI无关的代码将很快让你的程序出现问题。一个典型的代码异味就是从UIViewController
发起一个网络请求。
这些习惯会让你放入很多代码在UIViewController
中,这也让你离死期不远了。不要这样做!短期来说,你节约了几分钟,但长期来看,你可能会损失几个小时来debug或者在其他地方没办法复用这些代码。
当你检查视图层的时候参看一下以下的问题:
它和模型层(model layer)有交互吗?
它包含工作逻辑吗?
它会做与UI无关的事吗?
如果有任意一个问题你的答案是”是“,或许你该花点时间来清理和重构一下你的代码了。
当然,这些规则不是一成不变的,有时你还是会需要选择忽视它们。不管怎么说,在开发过程中需要时刻注意这些准则。
最后,如果你把这些类写得很好,你应该能随时复用他们。如果你不相信我,你只需要看看GitHub上面有多少UI元素。
控制层 Controller Layer
控制器层是你app中复用度最低的部分,因为它包含着你很多具体的操作逻辑。在你这里成立的代码不能在别人那里使用,这应该不会让你觉得意外。
通常来说,你会在控制层看到很多类来处理以下事情:
什么需要被首先访问:数据还是网络?
多久刷新一次你的app?
下一个界面应该是什么?在什么样的情景下?
如果app被推到后台,有什么需要被清理?
...
你应该把控制层看做app的大脑:它负责下一步怎么走。通常的情况下,你需要做大量的测试来保证控制层中的类都如预期一样工作。
一个栗子
以上是关于MVC模式:Massive View Controller?的主要内容,如果未能解决你的问题,请参考以下文章