mirror of
https://github.com/NohamR/knowledge-kit.git
synced 2026-05-24 20:00:37 +00:00
update: 更新内容
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
## 设计一个客户端校验器
|
||||
## 妙用设计模式来设计一个客户端校验器
|
||||
|
||||
> 订单在提交的时候会面临不同的校验规则,不同的校验规则会有不同的处理。假设这个处理就是弹窗。
|
||||
>
|
||||
@@ -146,12 +146,44 @@ typedef NS_ENUM(NSUInteger, OrderSubmitReminderType) {
|
||||
- 虽然抽取为不同方法,但是每个方法内部存在大量冗余代码,因为每个校验规则的代码是一样的,重复存在,只不过先后顺序不同
|
||||
- 存在隐含逻辑。 return 顺序决定了弹窗优先级的高低(这一点不够痛)
|
||||
|
||||
|
||||
|
||||
## 方案
|
||||
|
||||
那能不能优化呢?有2个思路:责任链设计模式、工厂设计模式
|
||||
|
||||
### 责任链设计模式
|
||||
|
||||
责任链模式即 Chain Of Responsibility,属于行为型模式。行为型模式不仅秒死对象或类的模式,还描述他们之间的通信模式,比如对操作的处理该如何传递等等。
|
||||
|
||||
为什么会有这个思路?
|
||||
|
||||
主要来源于2个方向:Node 的洋葱模式、移动端的点击事件传递。
|
||||
|
||||
移动端的事件响应模型:点击 view 看看能不能响应,不能响应则继续向上抛,知道抛到 window 为止;
|
||||
|
||||
前端 JS 事件冒泡机制:点击事件假设是动态绑定到 DOM 节点上的,浏览器本身不知道哪些地方会处理点击事件,但又要让每层 DOM 拥有对该点击事件的平等处理权,所以就诞生了事件冒泡和组织冒泡的能力 `event.stopPropagation()`
|
||||
|
||||
|
||||
|
||||
Node 洋葱模式:发送一个 Request 一层层中间件去处理,比如添加日志、添加请求拦截转发、处理核心业务逻辑、添加日志、添加自定义 response header等,一个中间件层只关注聚焦自己层需要做的事情,处理完继续向下一层抛。
|
||||
|
||||
设想下如果没有中间价模型,假设实现一个记录请求事件和自定义 HTTP Header 的需求,业务逻辑 curd 代码和记录请求时间和自定义 Header 代码全都杂糅在一起,难以维护。
|
||||
|
||||
责任链的核心就是:**使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系。将这些对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为止。**
|
||||
|
||||
- 降低处理者对象之间的耦合度。一个对象无须知道到底是哪一个对象处理其请求以及链的结构,发送者和接收者也无须拥有对方的明确信息。
|
||||
|
||||
- 增强了系统的可扩展性。可以根据业务需求增加或者调整新的请求处理类,满足开闭原则(类似维护链表的节点信息)
|
||||
|
||||
- 可插拔,增强了给对象指派职责的灵活性。当工作流程发生变化,可以动态地改变链内的成员或者调动它们的次序,也可动态地新增或者删除责任。
|
||||
|
||||
- 责任链简化了对象之间的连接。每个对象只需保持一个指向其后继者的引用,不需保持其他所有处理者的引用,这避免了使用众多的 if 或者 if···else 语句。
|
||||
|
||||
- 责任分担。每个类只需要处理自己该处理的工作,不该处理的传递给下一个对象完成,明确各类的责任范围,符合类的单一职责原则。
|
||||
|
||||
|
||||
|
||||
采用责任链设计模式。基类 `OrderSubmitBaseValidator` 声明接口,是一个抽象类:
|
||||
|
||||
- 有一个属性 `nextValidator` 用于指向下一个校验器
|
||||
@@ -273,6 +305,8 @@ let rulesMap = {
|
||||
3. 对于现有校验规则的修改足够收口,每个规则都有自己的 validator 和 validate 方法
|
||||
4. 目前弹窗优先级针对 EVA 、BTC 存在不同优先级顺序,如果按照现有的方案实施,则会存在很多冗余代码
|
||||
|
||||
|
||||
|
||||
### 工厂设计模式
|
||||
|
||||
设计基类
|
||||
@@ -355,4 +389,6 @@ OrderSumitValidatorFactory {
|
||||
- 没有重复逻辑,判断方法都守口在基类中
|
||||
- 优先级的关系维护在不同的子类中,各司其职,独立维护
|
||||
|
||||
最后选什么?组合优于继承,个人倾向使用责任链模式去组织。
|
||||
|
||||
|
||||
最后选什么?组合优于继承,个人倾向使用责任链模式去组织代码。
|
||||
@@ -366,6 +366,10 @@ Debug 设置为 NO, Release 设置为 YES 可减少可执行文件大小。
|
||||
|
||||
Xcode 默认会开启此选项,C/C++/Swift 等静态语言编译器会在 link 的时候移除未使用的代码,但是对于 Objective-C 等动态语言是无效的。因为 Objective-C 是建立在运行时上面的,底层暴露给编译器的都是 Runtime 源码编译结果,所有的部分应该都是会被判别为有效代码。
|
||||
|
||||
带来的好处:
|
||||
- App 可执行文件体积减少
|
||||
- 减少 App 分页(分页过多会容易引起内存引起缺页异常)
|
||||
|
||||
默认选项,不做修改。
|
||||
|
||||
#### 3.1.4 Apple Clang - Code Generation
|
||||
|
||||
@@ -113,4 +113,4 @@
|
||||
* [107、IM技术](https://github.com/FantasticLBP/knowledge-kit/blob/master/Chapter1%20-%20iOS/1.107.md)
|
||||
* [108、精准测试](https://github.com/FantasticLBP/knowledge-kit/blob/master/Chapter1%20-%20iOS/1.108.md)
|
||||
* [109、汇编学习](https://github.com/FantasticLBP/knowledge-kit/blob/master/Chapter1%20-%20iOS/1.109.md)
|
||||
* [110、设计一个客户端校验器](https://github.com/FantasticLBP/knowledge-kit/blob/master/Chapter1%20-%20iOS/1.110.md)
|
||||
* [110、妙用设计模式来设计一个客户端校验器](https://github.com/FantasticLBP/knowledge-kit/blob/master/Chapter1%20-%20iOS/1.110.md)
|
||||
Reference in New Issue
Block a user