<div class="article-holder unable-reprint"><p><br></p><h1 style="text-align: center;"><span class="color-pink-03 font-size-23">问题引入</span></h1><p>曾几何时,我其实也特别钟情于 <code class="prettyprint code-in-text prettyprinted"><span class="kwd">if</span><span class="pun">/</span><span class="kwd">else</span></code>连环写法,上来就是一顿<strong>SAO操作</strong></p><figure class="img-box"><img data-src="https://www.wenjie.store/65455ac23997aeee18234e4fa4216c63440e6408.png" width="126" height="100" data-size="14202" data-index="1" src="https://www.wenjie.store/65455ac23997aeee18234e4fa4216c63440e6408.png" class="loaded" style="width: 126px; height: 100px;"><figcaption class="caption"></figcaption></figure><p>比如这里<strong>举个好理解的简单栗子</strong>:</p><p>一般来说我们正常的后台管理系统都有所谓的角色的概念,不同管理员权限不一样,能够行使的操作也不一样,比如:</p><ul class=" list-paddingleft-2"><li><p>系统管理员( <code class="prettyprint code-in-text prettyprinted"><span class="pln">ROLE_ROOT_ADMIN</span></code>):有 <code class="prettyprint code-in-text prettyprinted"><span class="pln">A</span></code>操作权限</p></li><li><p>订单管理员( <code class="prettyprint code-in-text prettyprinted"><span class="pln">ROLE_ORDER_ADMIN</span></code>):有 <code class="prettyprint code-in-text prettyprinted"><span class="pln">B</span></code>操作权限</p></li><li><p>普通用户( <code class="prettyprint code-in-text prettyprinted"><span class="pln">ROLE_NORMAL</span></code>):有 <code class="prettyprint code-in-text prettyprinted"><span class="pln">C</span></code>操作权限</p></li></ul><p>比如一个用户进来,我们需要根据不同用户的角色来判断其有哪些行为,注意,这时候<strong>SAO代码</strong>出现了:</p><figure class="img-box"><img data-src="https://www.wenjie.store/JudgeRole.png" width="2386" height="1452" data-size="310722" data-index="2" src="https://www.wenjie.store/JudgeRole.png" class="loaded" style="width: 660px; height: 402px;"><figcaption class="caption"></figcaption></figure><p>这样写到底有什么不好呢?你想想看,假如系统里有<span class="color-pink-03"><strong>几十个角色</strong></span>,或者以后要是再加几个角色,那几十个 <code class="prettyprint code-in-text prettyprinted"><span class="kwd">if/else</span></code>嵌套可以说是非常酸爽了…… 这样<strong>一来</strong>非常<strong><span class="color-pink-03">不优雅</span></strong>,别人阅读起来很费劲;<strong>二来</strong>则是以后如果再复杂一点,或者想要再加条件的话<span class="color-pink-03"><strong>不好扩展</strong></span>;而且代码一改,以前的老功能肯定还得重测,岂不疯了……<br></p><p>当然有人会说用 <code class="prettyprint code-in-text prettyprinted"><span class="kwd">switch</span><span class="pun">/</span><span class="kwd">case</span></code>来写是否会优雅一些呢?答案是:<strong>毛区别都没有</strong>!</p><figure class="img-box"><img data-src="https://www.wenjie.store/扎铁了.png" width="198" height="198" data-size="31058" data-index="3" src="https://www.wenjie.store/扎铁了.png" class="loaded" style="width: 198px; height: 198px;"><figcaption class="caption"></figcaption></figure><blockquote><p>接下来简单讲几种改进方式,别再 <code class="prettyprint code-in-text prettyprinted"><span class="kwd">if</span><span class="pun">/</span><span class="kwd">else</span></code>走天下了</p></blockquote><h1 style="text-align: center;"><span class="color-pink-03"></span></h1><figure class="img-box"><img class="cut-off-1 loaded" src="https://www.wenjie.store/0117cbba35e51b0bce5f8c2f6a838e8a087e8ee7.png"></figure><h1 style="text-align: center;"><span class="color-pink-03"></span><span class="color-pink-03">有枚举为啥不用</span></h1><blockquote><p>什么角色能干什么事,这很明显有一个对应关系,所以学过的枚举为啥不用呢?</p></blockquote><p>首先定义一个公用接口 <code class="prettyprint code-in-text prettyprinted"><span class="typ">RoleOperation</span></code>,表示不同角色所能做的操作:</p><figure class="img-box"><img data-src="https://www.wenjie.store/RoleOperation.png" width="1410" height="338" data-size="55463" data-index="4" src="https://www.wenjie.store/RoleOperation.png" class="loaded" style="width: 660px; height: 158px;"><figcaption class="caption"></figcaption></figure><p>接下来我们将不同角色的情况全部交由枚举类来做,定义一个不同角色有不同权限的枚举类 <code class="prettyprint code-in-text prettyprinted"><span class="typ">RoleEnum</span></code>:</p><figure class="img-box"><img data-src="https://www.wenjie.store/RoleEnum.png" width="1080" height="1094" data-size="134272" data-index="5" src="https://www.wenjie.store/RoleEnum.png" class="loaded" style="width: 660px; height: 669px;"><figcaption class="caption"></figcaption></figure><p>接下来调用就变得异常简单了,一行代码就行了, <code class="prettyprint code-in-text prettyprinted"><span class="kwd">if</span><span class="pun">/</span><span class="kwd">else</span></code>也灰飞烟灭了:</p><figure class="img-box"><img data-src="https://www.wenjie.store/JudgeRole2.png" width="1958" height="566" data-size="110952" data-index="6" src="https://www.wenjie.store/JudgeRole2.png" class="loaded" style="width: 660px; height: 191px;"><figcaption class="caption"></figcaption></figure><p>而且这样一来,以后假如我想扩充条件,只需要去枚举类中加代码即可,而不是去改以前的代码,这岂不很稳!<br></p><figure class="img-box"><img data-src="https://www.wenjie.store/稳了稳了.png" width="86" height="89" data-size="7498" data-index="7" src="https://www.wenjie.store/稳了稳了.png" class="loaded" style="width: 86px; height: 89px;"><figcaption class="caption"></figcaption></figure><blockquote><p>除了用枚举来消除 <code class="prettyprint code-in-text prettyprinted"><span class="kwd">if</span><span class="pun">/</span><span class="kwd">else</span></code>,工厂模式也可以实现</p></blockquote><h1 style="text-align: center;"><span class="color-pink-03"></span></h1><figure class="img-box"><img class="cut-off-1 loaded" src="https://www.wenjie.store/0117cbba35e51b0bce5f8c2f6a838e8a087e8ee7.png"></figure><h1 style="text-align: center;"><span class="color-pink-03"></span><span class="color-pink-03">有工厂模式为啥不用</span></h1><p>不同分支做不同的事情,很明显就提供了使用工厂模式的契机,我们只需要将不同情况单独定义好,然后去工厂类里面<strong>聚合</strong>即可。</p><p>首先,针对不同的角色,单独定义其业务类:</p><figure class="img-box"><img data-src="https://www.wenjie.store/工厂模式RootAdminRole.png" width="1706" height="1204" data-size="176214" data-index="8" src="https://www.wenjie.store/工厂模式RootAdminRole.png" class="loaded" style="width: 660px; height: 466px;"><figcaption class="caption"></figcaption></figure><figure class="img-box"><img data-src="https://www.wenjie.store/OrderAdminRole.png" width="1762" height="1212" data-size="190213" data-index="9" src="https://www.wenjie.store/OrderAdminRole.png" class="loaded" style="width: 660px; height: 454px;"><figcaption class="caption"></figcaption></figure><figure class="img-box"><img data-src="https://www.wenjie.store/工厂模式NormalRole.png" width="1676" height="1214" data-size="169505" data-index="10" src="https://www.wenjie.store/工厂模式NormalRole.png" class="loaded" style="width: 660px; height: 478px;"><figcaption class="caption"></figcaption></figure><p>接下来再写一个<strong>工厂类 <code class="prettyprint code-in-text prettyprinted"><span class="typ">RoleFactory</span></code></strong>对上面不同角色进行<span class="color-pink-03"></span>聚合:</p><figure class="img-box"><img data-src="https://www.wenjie.store/工厂类RoleFactory.png" width="2696" height="1212" data-size="322248" data-index="11" src="https://www.wenjie.store/工厂类RoleFactory.png" class="loaded" style="width: 660px; height: 297px;"><figcaption class="caption"></figcaption></figure><p>接下来借助上面这个工厂,业务代码调用也只需一行代码, <code class="prettyprint code-in-text prettyprinted"><span class="kwd">if</span><span class="pun">/</span><span class="kwd">else</span></code>同样被消除了:</p><figure class="img-box"><img data-src="https://www.wenjie.store/JudgeRole3.png" width="1594" height="580" data-size="96553" data-index="12" src="https://www.wenjie.store/JudgeRole3.png" class="loaded" style="width: 660px; height: 240px;"><figcaption class="caption"></figcaption></figure><p>这样的话以后想扩展条件也很容易,只需要增加新代码,而不需要动以前的业务代码,非常符合<strong>“开闭原则”</strong>。</p><figure class="img-box"><img data-src="https://www.wenjie.store/可以可以.png" width="167" height="181" data-size="37114" data-index="13" src="https://www.wenjie.store/可以可以.png" class="loaded" style="width: 167px; height: 181px;"><figcaption class="caption"></figcaption></figure><blockquote><p>来,我们接着来,除了工厂模式,策略模式也不妨试一试</p></blockquote><h1 style="text-align: center;"><span class="color-pink-03"></span></h1><figure class="img-box"><img class="cut-off-1 loaded" src="https://www.wenjie.store/0117cbba35e51b0bce5f8c2f6a838e8a087e8ee7.png"></figure><h1 style="text-align: center;"><span class="color-pink-03"></span><span class="color-pink-03">有策略模式为啥不用</span></h1><p>策略模式和工厂模式写起来其实区别也不大!</p><p>在上面工厂模式代码的基础上,按照策略模式的指导思想,我们也来创建一个所谓的<strong>策略上下文类</strong>,这里命名为 <code class="prettyprint code-in-text prettyprinted"><span class="typ">RoleContext</span></code>:</p><figure class="img-box"><img data-src="https://www.wenjie.store/策略模式RoleContext.png" width="1636" height="1124" data-size="175102" data-index="14" src="https://www.wenjie.store/策略模式RoleContext.png" class="loaded" style="width: 660px; height: 453px;"><figcaption class="caption"></figcaption></figure><p>很明显上面传入的参数 <code class="prettyprint code-in-text prettyprinted"><span class="pln">operation</span></code>就是表示不同的<strong>“策略”</strong>。我们在业务代码里传入不同的角色,即可得到不同的操作结果:</p><figure class="img-box"><img data-src="https://www.wenjie.store/JudgeRole4(策略模式).png" width="2360" height="1454" data-size="349645" data-index="15" src="https://www.wenjie.store/JudgeRole4(策略模式).png" class="loaded" style="width: 660px; height: 407px;"><figcaption class="caption"></figcaption></figure><h1 style="text-align: center;"><span class="font-size-23"><strong><span class="color-pink-03">后 记</span></strong></span></h1><p>好啦,先讲到这里吧,本文仅仅是抛砖引玉,使用了一个极其简单的示例来打了个样,然而其思想可以广泛地应用于实际复杂的业务和场景,思想真的很重要!写代码前还是得多思考一番,考虑是否有<span class="color-pink-03"><strong>更具扩展性的写法</strong></span>。</p><figure class="img-box focused"><img data-src="https://www.wenjie.store/奥利给.png" width="240" height="240" data-size="85952" data-index="16" src="https://www.wenjie.store/奥利给.png" class="loaded" style="width: 240px; height: 240px;"><figcaption class="caption"></figcaption></figure><p><br></p></div>
<blockquote><p>
原文地址:https://www.bilibili.com/read/cv4257620
</p></blockquote>
【转载】答应我,别再if/else走天下了可以吗