2017.6.15 第二次作业日志打印OCP重构 第一次提交#421
Merged
onlyliuxin merged 4 commits intoonlyliuxin:masterfrom Jun 20, 2017
Merged
Conversation
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
问题
重构一个简单的log打印,使之符合开闭原则(OCP)
解题
这个星期的作业似乎比上个星期的要简单,重构起来思路也很清晰,不过仍然有一些令我迷惑的地方,这个也在下面会讲到
分析
如图只有5个文件,功能分别为
在log中拼接上时间信息
提供主log方法
使用邮件发送log
使用sms发送log
当然啦,我相信这些方法都是瞎掰的,所以不用管,其实只要看一下Logger这个类中的方法就可以了,Logger类内容如下
一看就是要重构的代码,违反OCP原则的代码有个比较明显的特征就是使用了很多
if else或switch等分支语句对传进来的参数进行判断,而我重构的任务就是使用多态和继承来把这些分支语句去掉,或者说拆分开。那么可以发现这里的重构是分为两部分,一部分是用来判断log文本是否需要进行某种“加工”处理,比如添加时间信息
另一部分就是用来判断log需要通过什么方式发送出去
知道我要重构的目标代码,接下来就是拆分了
重构
log文本加工判断部分的重构
前面我说出现迷惑的地方就是这里,因为原代码中只有两种情况:加日期/不加日期,我一开始就在纠结,加不加日期的这个判断是否需要重构?毕竟只有两种情况就是应该用
if来处理的啊,把这个也拆分开来会不会过度设计了,但是我转念就想通了,我犯了和我第一次作业同样的错误,就是抽象程度不足,事实上这部分的代码正确的抽象应该是对log文本进行处理,而不仅仅只是加不加日期,所以除了加日期,以后还有可能加上类名啊,作者名啊什么乱七八糟的,所以这样看来一个if显然是不能胜任的,所以这一段代码也是要进行拆分的。讲完这一部分剩下的就简单了,++套路就是通过从一个基类继承实现传参的多态性,再通过基类实现某个动作的结构来实现功能的多态性++(这句话是我自己瞎掰的……不严谨,意思到了就行),所以重构如下:
一个接口IMsgHandle.java
一个基类BaseMsgTool.java
然后就是从基类继承的各种子类
HandleMsgWithNone.java
HandleMsgWithDate.java
判断log需要通过什么方式发送部分的重构
和上面一样就不多赘述了
一个接口ISendLog.java
一个基类BaseLog.java
然后就是从基类继承的各种子类
EmailLog.java
SmsLog.java
PrintLog.java
Logger类变成什么样了?
经过重构之后,Logger类变成了
然后再其他类中的调用就变成了
至此,我的重构就完成了,但我觉得还是有点什么不对……到底是什么不对呢?
小结
开闭原则是复用代码的基石,继承基类然后通过多态来实现
if的效果,可以达到在调用的时候不需要改原来调用的方法就直接添加新的子类,大大提高了扩展性和可维护性。总结
略,等老师点评