文章目录
前言
"MVC",即Model(模型),View(视图),Controller(控制器),MVC模式是架构模式的一种。
关于"架构模式":
架构模式(Architectural Pattern)是软件架构中常见的组织结构解决方案,用于指导大型软件系统的设计。它们描述了软件系统常见的组织结构和它们之间的相互关系,为构建复杂软件系统提供了经验证的解决方案。架构模式提供了一种通用的、可重用的解决方案来处理在软件设计中遇到的常见问题。
常见的架构模式包括:
1.分层模式(Layered Pattern) :
将系统分割成多个层次,每一层提供特定的服务,并且只与相邻层次通信。例如,一个典型的三层架构包括表示层(用户界面)、业务逻辑层和数据访问层。
2.客户端-服务器模式(Client-Server Pattern) :
系统分为两部分:服务器提供服务,客户端请求服务。这种模式广泛应用于网络应用程序。
3.模型-视图-控制器模式(Model-View-Controller Pattern, MVC) :
用于实现用户界面的分离关注点,将应用程序分为三个核心组件:模型(数据和业务逻辑)、视图(用户界面)和控制器(业务逻辑和用户界面之间的通信)。
4.管道-过滤器模式(Pipeline-Filter Pattern) :
在这种模式中,每个处理步骤(过滤器)作为数据流(管道)中的一个阶段,数据流从一个过滤器流向下一个过滤器。
5.事件驱动架构模式(Event-Driven Pattern) :
系统作为一系列异步事件和回调处理函数的集合。这种模式适用于需要高响应性和可伸缩性的应用。
6.微内核模式(Microkernel Pattern) :
系统的核心功能由一个小型的、可扩展的内核提供,其他功能则作为插件或模块附加在内核周围。
7.代理模式(Proxy Pattern) :
为其他对象提供一个代理或占位符,以控制对这个对象的访问。这在远程代理、虚拟代理和保护代理中很常见。
8.发布-订阅模式(Publish-Subscribe Pattern) :
一种事件驱动的通信模式,发布者发送事件,而订阅者对这些事件做出响应,但发布者和订阅者之间没有直接的联系。
9.黑板模式(Blackboard Pattern) :
多个模块或组件通过一个共享的数据空间(黑板)进行通信和协作,以解决复杂问题。
10.MVC的变体模式 :
包括表现层-业务逻辑层-数据访问层(Presentation-Logic-Data Access, PLDA)、模型-视图-视图模型(Model-View-ViewModel, MVVM)和模型-视图-适配器(Model-View-Adapter, MVA)等。
MVC架构模式
基本概念
'M'------模型(Model):视图类所需要的数据,例如:表格需要显示的文字。
'V'------视图(View):屏幕上显示的UI,响应用户事件,接受用户输入。例如:按钮,标签,进度条等。
'C'------控制器(Controller):连接视图类和模型类,任务是使数据显示在屏幕上,主要负责转发请求,对请求进行处理。例如:控制器将表格需要使用的数据"填入"表格视图中,将表格视图显示出来。
关于这三者的关系,我参考了如下图例来理解:
斯坦福大学的iOS公开课第一课:
苹果官方的图解:
在这里可以看出来"V"和"M"是相互独立的,在iOS开发的MVC框架中,我们可以理解为view和model相互独立,两者属于不知道对方的存在的陌生人关系。
⚠️Model 和 View 是相互独立的
这是很容易犯错的一点,因为MVC 架构模式是在软件设计中通用的,不只是iOS 开发。iOS 开发中的MVC模式是基于传统的MVC 架构的,只是在具体实现上有所不同。Apple 官方对于iOS开发中的MVC 模式和传统的MVC 架构有所不同,如果查阅传统的MVC 架构会发现,View 和Model 之间是有通信的。
(转自 SungKaikai 文章链接)
通信方式
- 控制器C可以直接访问模型M:将模型直接作为控制器的属性。
- 控制器C可以直接访问视图V:将视图直接作为控制器的属性。
- 模型M与视图V无法直接访问对方:二者完全解耦,不能引用对方,把对方设置为属性。
- 视图V到控制器C的通信:
目标动作机制(target - action):用户与视图交互触发控制器的方法。例如:点击按钮后实现视界面跳转,网络请求,刷新UI等。
委托机制(delegate):视图向控制器询问某些自己无法决定的事情,或是让控制器帮助自己做一些自己独立无法完成的事情。 因为控制器才是掌握全局的角色,很多时候视图是无法自己做决定的。例如:表格问控制器:我可以滚动么?然后控制器给予回答告知是否可以继续滚动。 如果表格的高度很小,那么就可以不让它滚动。但是如果表格的高度已经超过了屏幕的高度,这时候如果让它自作主张无法滚动就不好了。
数据源机制(dataSource):视图让控制器给它将要显示的数据。例如:音乐的数据存在于模型里,控制器访问模型,从模型里拿到数据后告诉视图如何显示出歌曲。 - 模型M到控制器C的通信
广播机制(Notification):控制器注册监听某模型数据变化的广播频道,当此模型数据变化后向该控制器发送广播,告知模型变化情况。
KVO机制(Key-Value Observing):模型作为控制器的属性,当模型属性被修改后,持有此模型属性的控制器就会收到通知。
------斯坦福大学iOS开发公开课总结(一):iOS的MVC框架
简单应用
先看看创建的文件:
1.创建 Model
模型通常是一个或多个类,它们包含数据和对数据进行操作的方法。例如,一个简单的Person测试模型:
objectivec
#import <Foundation/Foundation.h>
NS_ASSUME_NONNULL_BEGIN
@interface TestModel : NSObject
@property (nonatomic, strong) NSString *name;
@property (nonatomic, strong) NSNumber *age;
- (void)performAction;
@end
NS_ASSUME_NONNULL_END
objectivec
#import "TestModel.h"
@implementation TestModel
- (void)performAction {
// 这里可以放置一些业务逻辑,例如打印一条消息
NSLog(@"Hello, my name is %@ and I am %@ years old.", self.name, self.age);
}
@end
这里的代码存在一些bug,后续笔者修改后会再呈现完整代码。
总结
在模型类里是不能调用控制器的方法的,模型类只能被控制器调用并且当所拥有的数据改变后通知使用自己的控制器数据的改变。更不能直接给视图通知让视图自己更新UI。