不知道怎么提高代码质量?来看看这几种设计模式吧! (3)

备忘录模式类似于JS经常使用的缓存函数,内部记录一个状态,也就是缓存,当我们再次访问的时候可以直接拿缓存数据:

function memo() { const cache = {}; return function(arg) { if(cache[arg]) { return cache[arg]; } else { // 没缓存的时候先执行方法,得到结果res // 然后将res写入缓存 cache[arg] = res; return res; } } 实例:文章缓存

这个例子在实际项目中也比较常见,用户每次点进一个新文章都需要从API请求数据,如果他下次再点进同一篇文章,我们可能希望直接用上次请求的数据,而不再次请求,这时候就可以用到我们的备忘录模式了,直接拿上面的结构来用就行了:

function pageCache(pageId) { const cache = {}; return function(pageId) { // 为了保持返回类型一致,我们都返回一个Promise if(cache[pageId]) { return Promise.solve(cache[pageId]); } else { return axios.get(pageId).then((data) => { cache[pageId] = data; return data; }) } } }

上述代码用了备忘录模式来解决这个问题,但是代码比较简单,实际项目中可能需求会更加复杂一些,但是这个思路还是可以参考的。

实例:前进后退功能

这个例子的需求是,我们需要做一个可以移动的DIV,用户把这个DIV随意移动,但是他有时候可能误操作或者反悔了,想把这个DIV移动回去,也就是将状态回退到上一次,有了回退状态的需求,当然还有配对的前进状态的需求。这种类似的需求我们就可以用备忘录模式实现:

function moveDiv() { this.states = []; // 一个数组记录所有状态 this.currentState = 0; // 一个变量记录当前状态位置 } // 移动方法,每次移动记录状态 moveDiv.prototype.move = function(type, num) { changeDiv(type, num); // 伪代码,移动DIV的具体操作,这里并未实现 // 记录本次操作到states里面去 this.states.push({type,num}); this.currentState = this.states.length - 1; // 改变当前状态指针 } // 前进方法,取出状态执行 moveDiv.prototype.forward = function() { // 如果当前不是最后一个状态 if(this.currentState < this.states.length - 1) { // 取出前进的状态 this.currentState++; const state = this.states[this.currentState]; // 执行该状态位置 changeDiv(state.type, state.num); } } // 后退方法是类似的 moveDiv.prototype.forward = function() { // 如果当前不是第一个状态 if(this.currentState > 0) { // 取出后退的状态 this.currentState--; const state = this.states[this.currentState]; // 执行该状态位置 changeDiv(state.type, state.num); } }

上述代码通过一个数组将用户所有操作过的状态都记录下来了,用户可以随时在状态间进行前进和后退。

总结

本文讲的这几种设计模式策略/状态模式,外观模式,迭代器模式,备忘录模式都很好理解,而且在实际工作中也非常常见,熟练使用他们可以有效减少冗余代码,提高我们的代码质量。

策略模式通过将我们的if条件改写为一条条的策略减少了if...else的数量,看起来更清爽,扩展起来也更方便。状态模式跟策略模式很像,只是还多了一个状态,可以根据这个状态来选取具体的策略。

外观模式可能我们已经在无意间使用了,就是将模块一些内部逻辑封装在一个更高级的接口内部,或者将一些类似操作封装在一个方法内部,从而让外部调用更加方便。

迭代器模式在JS数组上有很多实现,我们也可以模仿他们做一下数据处理的工作,特别适合处理从API拿来的大量结构相似的数据。

备忘录模式就是加一个缓存对象,用来记录之前获取过的数据或者操作的状态,后面可以用来加快访问速度或者进行状态回滚。

还是那句话,设计模式的重点在于理解思想,实现方式可以多种多样。

本文是讲设计模式的最后一篇文章,前面三篇是:

(500+赞!)不知道怎么封装代码?看看这几种设计模式吧!

(100+赞!)框架源码中用来提高扩展性的设计模式

不知道怎么提高代码复用性?看看这几种设计模式吧

文章的最后,感谢你花费宝贵的时间阅读本文,如果本文给了你一点点帮助或者启发,请不要吝啬你的赞和GitHub小星星,你的支持是作者持续创作的动力。

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/wpwjps.html