ホームページ php教程 php手册 PHP の 3 層構造 (その 2) PHP は AOP を実装します

PHP の 3 層構造 (その 2) PHP は AOP を実装します

Jul 11, 2016 pm 08:00 PM
aop php コード 成し遂げる オープンソース 構造 プログラミング プログラミング言語 ソフトウェア開発

  • この記事のソースコードのダウンロードアドレス: http://files.cnblogs.com/afritxia2008/TraceLWord.rar
  • 開発環境はeclipse(pdt)です

中間サービス層に焦点を当てましょう。中間サービス層のコードは比較的単純で、データ アクセス層のコードを呼び出してメッセージをデータベースに保存するだけです。コード 1 に示すように:

リーリー

掲示板のデモを見た後、企業の製品部門やマーケティング部門がさまざまなアイデアやニーズを提案する可能性があります。たとえば、メッセージを追加する前にユーザーの権限を確認したいと考えています。メッセージを残せるのは登録ユーザーだけです!コード 2 に示すように、コードを変更する必要があります:

リーリー

マーケティング部門もメッセージを追加する前に内容を確認したいと考えており、メッセージに汚い言葉が含まれている場合は保存されません。コード 3 に示すように、コードの変更を続けます:

リーリー

製品部門も新しい要件を提示し、ポイントメカニズムへの参加を希望しています。具体的には、メッセージを残すことに成功するたびに、ユーザーに +5 ポイントが与えられます。コード 4 に示すように、コードの変更を続けます。

リーリー

その後間もなく、製品部門はユーザーが 1,000 ポイントを蓄積するたびにアップグレードされることを望んでいます。コード 5 に示すように、コードの変更を続けます。

リーリー

需要が増加するにつれて、中間サービス層のコードを常に変更する必要があります。 しかし、要求が増えれば増えるほど、中間サービス層のコードがより多く、より大きくなるということは、難しくないはずです。結局のところ、3 層構造の開発モデルを使用しても、プロジェクトの難易度を効果的に下げることはできません。 さらに、需要の変化に応じて中間サービス コードを変更した後は、新しいコードを効果的にテストするのではなく、すべてのコードを再テストする必要があります...

実際、この掲示板のコードを注意深く分析してみましょう。まず、プライマリ ビジネス ロジックとセカンダリ ビジネス ロジックの概念を提案する必要があります。 何はともあれ、メッセージの内容をデータベースに保存することがビジネス ロジックのバックボーンです。これが主要なビジネス ロジックです。需要が増加したため、このセクションは変更されていません。 データベースに保存する前の権限の確認と内容のチェック、データベースに保存した後のユーザーへのポイントの追加とユーザーのアップグレードについては、これらはすべて前処理と仕上げの作業であり、すべて二次的なビジネス ロジックです。メインのビジネス ロジックはほとんど変わりませんが、二次的なビジネス ロジックは非常に頻繁に変更されます。コードの可読性と保守性を向上させるために、これらの二次的なビジネス ロジックを別の場所に配置し、メインのビジネス ロジックに干渉しないようにすることを検討できます。メインのビジネス ロジックは、実行すべきことに集中する必要があります。その他のことについては、メインのビジネス ロジックは気にしません。コード 6 に示すように、コードは次のように記述できます。

リーリー

許可判定コードとメッセージ内容テキストフィルタリングコードをbeforeAppend関数に、ユーザーポイントコードをbehindAppend関数に入れることで、メインのビジネスロジックコードから二次的なビジネスロジックをクリーンアップすることができます。メイン ビジネス ロジックは、Append の前に「オーバーチュア」関数があり、Append の後ろに「エピローグ」関数があることを知っていますが、メイン ビジネス ロジックは、オーバーチュア関数とエピローグ関数で具体的に何が行われるかを知りませんし、知る必要もありません。もちろん、実際のコーディング作業はそれほど単純ではありません。製品部門やマーケティング部門のニーズの変化も考慮する必要があるため、その変化に対応するにはプラグイン方式を導入するのが最善ですが、それだけに頼っています。 beforeAppend と BehindAppend の 2 つの関数では、この目的を達成するための最良の方法です~

プラグインメソッドを実装したい場合は、インターフェースを作成できます。

インターフェイスを使用する利点は、定義と実装を分離できること、もう 1 つはポリモーフィズムを実現できることです。 メッセージ拡張インターフェイス ILWordExtension を作成します。これには、beforeAppend と BehindAppend の 2 つの関数があります。権限の検証、コンテンツ チェック、ボーナス ポイントなどの機能は、ILWordExtension インターフェイスを実装する 3 つの実装クラスとみなすことができます。主要なビジネス ロジックは、これら 3 つの実装クラスを横断して、二次的なビジネス ロジックを完成させます。図 1 に示すように:

PHP の 3 層構造 (その 2) PHP は AOP を実装します

(写真1)、拡張インターフェースを追加します

CheckPowerExtension 拡張クラスはユーザーの権限を確認するために使用され、CheckContentExtension 拡張クラスはメッセージの内容を確認するために使用され、AddScoreExtension 拡張クラスはユーザーにポイントを追加しアップグレードするために使用されます。回路図コードはコード 7 に示されています:

リーリー

 

如果还有新需求,,我们只要再添加ILWordExtension 实现类并且把它注册到getExtArray函数里即可。程序从此有了条理,并且算是具备了可扩展性。

 

不过先不要忙着高兴,有个问题就在这个可扩展性里。当新的需求被提出之后,我们可以再添加 ILWordExtension 实现类,这个的确正确。但是将这个新类注册到getExtArray函数里,等于说还是要修改主业务逻辑代码。能不能不修改呢?每次有新的需求变化还是要告知主业务逻辑,这样终归不太好。最理想的情况是新的扩展代码加入系统之后,主业务逻辑代码不用修改,因为主业务逻辑根本不知道有新扩展这回事!为此我们还需要优化一下设计方案,如图2所示:

 

PHP の 3 層構造 (その 2) PHP は AOP を実装します

(图2),加入扩展家族类

 

对于调用扩展的主程序(也就是中间服务类LWordServiceCore),只让它知道有ILWordExtension(扩展)这件事就可以了,它不需要知道还有CheckPowerExtension(检查权限扩展)、CheckContentExtension(检查内容扩展)和AddScoreExtension(加分扩展)这三个类。对这三个类的调用过程被移动到LWordExtensionFamily (扩展家族类)里去了。

 

LWordExtensionFamily其实就是一个能存放多个ILWordExtension接口实例的容器类,从图2中可以看出这个容器类不仅仅是实现了ILWordExtension接口,而且还聚合多个ILWordExtension接口的实例,所以它很特殊!对于LWordServiceCore类,这个类只知道ILWordExtension接口,但并不知道这个接口存在三个实现类。恰好LWordExtensionFamily类就实现了ILWordExtension接口,这很好的符合了中间服务类的要求,并且这个扩展家族类知道ILWordExtension存在三个实现类,并会一一调用它们, LWordExtensionFamily代码大概如代码8所示:

 

<div>
<!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #008000;">//</span><span style="color: #008000;"> 代码 8, 扩展家族<br>// 扩展家族</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">class</span><span style="color: #000000;"> LWordExtensionFamily </span><span style="text-decoration: underline;"><span style="color: #0000ff;">implements</span></span><span style="color: #000000;"><span style="text-decoration: underline;"> ILWordExtension</span> {<br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 扩展数组</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">private</span><span style="color: #000000;"> </span><span style="color: #800080;">$_extensionArray</span><span style="color: #000000;"> </span><span style="color: #000000;">=</span><span style="color: #000000;"> </span><span style="color: #0000ff;">array</span><span style="color: #000000;">();<br><br><span style="background-color: #e0e0e0;">    </span></span><span style="background-color: #e0e0e0;"><span style="color: #008000;">//</span><span style="color: #008000;"> 添加扩展</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> addExtension(ILWordExtension </span><span style="color: #800080;">$extension</span><span style="color: #000000;">) {<br>        </span><span style="color: #800080;">$this</span><span style="color: #000000;">-></span><span style="color: #000000;">_extensionArray []</span><span style="color: #000000;">=</span><span style="color: #000000;"> </span><span style="color: #800080;">$extension</span></span><span style="color: #000000;"><span style="background-color: #e0e0e0;">;<br>    }</span><br><br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言前</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> beforeAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br><span style="background-color: #e0e0e0;">        </span></span><span style="background-color: #e0e0e0;"><span style="color: #0000ff;">foreach</span><span style="color: #000000;"> (</span><span style="color: #800080;">$this</span><span style="color: #000000;">-></span><span style="color: #000000;">_extensionArray </span><span style="color: #0000ff;">as</span><span style="color: #000000;"> </span><span style="color: #800080;">$extension</span><span style="color: #000000;">) {<br>            </span><span style="color: #800080;">$extension</span><span style="color: #000000;">-></span><span style="color: #000000;">beforeAppend(</span><span style="color: #800080;">$newLWord</span></span><span style="color: #000000;"><span style="background-color: #e0e0e0;">);<br>        }</span><br>    }<br><br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言后</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> behindAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br><span style="background-color: #e0e0e0;">        </span></span><span style="background-color: #e0e0e0;"><span style="color: #0000ff;">foreach</span><span style="color: #000000;"> (</span><span style="color: #800080;">$this</span><span style="color: #000000;">-></span><span style="color: #000000;">_extensionArray </span><span style="color: #0000ff;">as</span><span style="color: #000000;"> </span><span style="color: #800080;">$extension</span><span style="color: #000000;">) {<br>            </span><span style="color: #800080;">$extension</span><span style="color: #000000;">-></span><span style="color: #000000;">behindAppend(</span><span style="color: #800080;">$newLWord</span></span><span style="color: #000000;"><span style="background-color: #e0e0e0;">);<br>        }</span><br>    }<br>}<br></span>
</div>
ログイン後にコピー

 

通过代码8不难看出LWordExtensionFamily类虽然也实现了ILWordExtension接口,但是它并不做任何实质的操作,而是通过循环语句将调用过程一一传递下去。为了平滑实现扩展到插入的方式,所以最好创建一个工厂类MyExtensionFactory。如代码9所示:

 

<div>
<!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #008000;">//</span><span style="color: #008000;"> 代码 9<br>// 自定义扩展工厂</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">class</span><span style="color: #000000;"> MyExtensionFactory {<br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 创建留言扩展</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">static</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> createLWordExtension() {<br><span style="background-color: #e0e0e0;">        </span></span><span style="background-color: #e0e0e0;"><span style="color: #800080;">$lwef</span><span style="color: #000000;"> </span><span style="color: #000000;">=</span><span style="color: #000000;"> </span><span style="color: #0000ff;">new</span><span style="color: #000000;"> LWordExtensionFamily();<br>        </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加扩展</span><span style="color: #008000;"><br></span><span style="color: #000000;">        </span><span style="color: #800080;">$lwef</span><span style="color: #000000;">-></span><span style="color: #000000;">addExtension(</span><span style="color: #0000ff;">new</span><span style="color: #000000;"> CheckPowerExtension());<br>        </span><span style="color: #800080;">$lwef</span><span style="color: #000000;">-></span><span style="color: #000000;">addExtension(</span><span style="color: #0000ff;">new</span><span style="color: #000000;"> CheckContentExtension());<br>        </span><span style="color: #800080;">$lwef</span><span style="color: #000000;">-></span><span style="color: #000000;">addExtension(</span><span style="color: #0000ff;">new</span><span style="color: #000000;"> AddScoreExtension());<br><br>        </span><span style="color: #0000ff;">return</span><span style="color: #000000;"> </span><span style="color: #800080;">$lwef</span></span><span style="color: #000000;"><span style="background-color: #e0e0e0;"><span style="background-color: #e0e0e0;">;<br>     <span style="color: #008000;">// 注意这里返回的是扩展家族类对象, <br>     // 扩展家族 LWordExtensionFamily 恰好也实现了接口 ILWordExtension, <br>     // 所以这是符合业务逻辑的要求. <br>     // 从此, 业务逻辑可以不关心具体的扩展对象, 只要知道扩展家族即可</span></span><br></span>    }<br>}<br></span>
</div>
ログイン後にコピー

 

使用扩展工厂类的好处就是可以随意的添加和移除扩展实例,这就很好的实现了可插入式编程。对于LWordServiceCore类只知道一个ILWordExtension接口,对于LWordExtensionFamily知道需要一一调用每个扩展,但是具体会有多少个扩展是通过MyExtensionFactory给出的。各负其责结构也很清晰。如果我们做一个假设,MyExtensionFactory类的createLWordExtension函数不是通过new关键字这样的硬编码方式来添加扩展列表,而是通过更巧妙的读取配置文件的方式来得到扩展列表,那么是不是更方便更灵活呢?不过这个就不再本文中讨论了。

 

中间服务层通过工厂类取得一个ILWordExtension接口的具体实例,然后调用其beforeAppend和behindAppend方法。当然中间服务并不知道工厂类返回的其实是一个含有多个ILWordExtension实例的容器(因为这个容器也实现了ILWordExtension接口),所以中间服务也就不知道扩展是被一一调用的。完整代码如代码10所示:

 

<div>
<!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #008000;">//</span><span style="color: #008000;"> 代码 10, 完整代码<br>// 扩展接口</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">interface</span><span style="color: #000000;"> ILWordExtension {<br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言前</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> beforeAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">);<br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言后</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> behindAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">);<br>};<br><br></span><span style="color: #008000;">//</span><span style="color: #008000;"> 检查权限</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">class</span><span style="color: #000000;"> CheckPowerExtension </span><span style="color: #0000ff;">implements</span><span style="color: #000000;"> ILWordExtension {<br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言前</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> beforeAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br>        </span><span style="color: #008000;">//</span><span style="color: #008000;"> 在这里判断用户权限</span><span style="color: #008000;"><br></span><span style="color: #000000;">    }<br><br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言后</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> behindAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br>    }<br>};<br><br></span><span style="color: #008000;">//</span><span style="color: #008000;"> 检查留言文本</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">class</span><span style="color: #000000;"> CheckContentExtension </span><span style="color: #0000ff;">implements</span><span style="color: #000000;"> ILWordExtension {<br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言前</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> beforeAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br>        </span><span style="color: #0000ff;">if</span><span style="color: #000000;"> (</span><span style="color: #008080;">stristr</span><span style="color: #000000;">(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">,</span><span style="color: #000000;"> </span><span style="color: #000000;">"</span><span style="color: #000000;">fuck</span><span style="color: #000000;">"</span><span style="color: #000000;">))<br>            </span><span style="color: #0000ff;">throw</span><span style="color: #000000;"> </span><span style="color: #0000ff;">new</span><span style="color: #000000;"> </span><span style="color: #0000ff;">Exception</span><span style="color: #000000;">();<br>    }<br><br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言后</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> behindAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br>    }<br>};<br><br></span><span style="color: #008000;">//</span><span style="color: #008000;"> 用户积分</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">class</span><span style="color: #000000;"> AddScoreExtension </span><span style="color: #0000ff;">implements</span><span style="color: #000000;"> ILWordExtension {<br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言前</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> beforeAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br>    }<br><br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言后</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> behindAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br>        </span><span style="color: #008000;">//</span><span style="color: #008000;"> 在这里给用户积分</span><span style="color: #008000;"><br></span><span style="color: #000000;">    }<br>};<br><br></span><span style="color: #008000;">//</span><span style="color: #008000;"> 扩展家族</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">class</span><span style="color: #000000;"> LWordExtensionFamily </span><span style="color: #0000ff;">implements</span><span style="color: #000000;"> ILWordExtension {<br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 扩展数组</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">private</span><span style="color: #000000;"> </span><span style="color: #800080;">$_extensionArray</span><span style="color: #000000;"> </span><span style="color: #000000;">=</span><span style="color: #000000;"> </span><span style="color: #0000ff;">array</span><span style="color: #000000;">();<br><br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加扩展</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> addExtension(ILWordExtension </span><span style="color: #800080;">$extension</span><span style="color: #000000;">) {<br>        </span><span style="color: #800080;">$this</span><span style="color: #000000;">-></span><span style="color: #000000;">_extensionArray []</span><span style="color: #000000;">=</span><span style="color: #000000;"> </span><span style="color: #800080;">$extension</span><span style="color: #000000;">;<br>    }<br><br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言前</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> beforeAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br>        </span><span style="color: #0000ff;">foreach</span><span style="color: #000000;"> (</span><span style="color: #800080;">$this</span><span style="color: #000000;">-></span><span style="color: #000000;">_extensionArray </span><span style="color: #0000ff;">as</span><span style="color: #000000;"> </span><span style="color: #800080;">$extension</span><span style="color: #000000;">) {<br>            </span><span style="color: #800080;">$extension</span><span style="color: #000000;">-></span><span style="color: #000000;">beforeAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">);<br>        }<br>    }<br><br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言后</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> behindAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br>        </span><span style="color: #0000ff;">foreach</span><span style="color: #000000;"> (</span><span style="color: #800080;">$this</span><span style="color: #000000;">-></span><span style="color: #000000;">_extensionArray </span><span style="color: #0000ff;">as</span><span style="color: #000000;"> </span><span style="color: #800080;">$extension</span><span style="color: #000000;">) {<br>            </span><span style="color: #800080;">$extension</span><span style="color: #000000;">-></span><span style="color: #000000;">behindAppend(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">);<br>        }<br>    }<br>}<br><br></span><span style="color: #008000;">//</span><span style="color: #008000;"> 自定义扩展工厂</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">class</span><span style="color: #000000;"> MyExtensionFactory {<br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 创建留言扩展</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">static</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> createLWordExtension() {<br>        </span><span style="color: #800080;">$lwef</span><span style="color: #000000;"> </span><span style="color: #000000;">=</span><span style="color: #000000;"> </span><span style="color: #0000ff;">new</span><span style="color: #000000;"> LWordExtensionFamily();<br>        </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加扩展</span><span style="color: #008000;"><br></span><span style="color: #000000;">        </span><span style="color: #800080;">$lwef</span><span style="color: #000000;">-></span><span style="color: #000000;">addExtension(</span><span style="color: #0000ff;">new</span><span style="color: #000000;"> CheckPowerExtension());<br>        </span><span style="color: #800080;">$lwef</span><span style="color: #000000;">-></span><span style="color: #000000;">addExtension(</span><span style="color: #0000ff;">new</span><span style="color: #000000;"> CheckLWordExtension());<br>        </span><span style="color: #800080;">$lwef</span><span style="color: #000000;">-></span><span style="color: #000000;">addExtension(</span><span style="color: #0000ff;">new</span><span style="color: #000000;"> AddScoreExtension());<br><br>        </span><span style="color: #0000ff;">return</span><span style="color: #000000;"> </span><span style="color: #800080;">$lwef</span><span style="color: #000000;">;<br>    }<br>}<br><br></span><span style="color: #008000;">//</span><span style="color: #008000;"> 中间服务层</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">class</span><span style="color: #000000;"> LWordServiceCore </span><span style="color: #0000ff;">implements</span><span style="color: #000000;"> ILWordService {<br>    </span><span style="color: #008000;">//</span><span style="color: #008000;"> 添加留言</span><span style="color: #008000;"><br></span><span style="color: #000000;">    </span><span style="color: #0000ff;">public</span><span style="color: #000000;"> </span><span style="color: #0000ff;">function</span><span style="color: #000000;"> append(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">) {<br><span style="background-color: #e0e0e0;">        </span></span><span style="background-color: #e0e0e0;"><span style="color: #008000;">//</span><span style="color: #008000;"> 获取扩展</span><span style="color: #008000;"><br></span><span style="color: #000000;">        </span><span style="color: #800080;">$ext</span><span style="color: #000000;"> </span><span style="color: #000000;">=</span><span style="color: #000000;"> MyExtensionFactory</span><span style="color: #000000;">::</span><span style="color: #000000;">createLWordExtension();<br><br>        </span><span style="color: #800080;">$ext</span><span style="color: #000000;">-></span><span style="color: #000000;">beforeAppend(</span><span style="color: #800080;">$newLWord</span></span><span style="color: #000000;"><span style="background-color: #e0e0e0;">);</span><br><br>        </span><span style="color: #008000;">//</span><span style="color: #008000;"> 调用数据访问层</span><span style="color: #008000;"><br></span><span style="color: #000000;">        </span><span style="color: #800080;">$dbTask</span><span style="color: #000000;"> </span><span style="color: #000000;">=</span><span style="color: #000000;"> </span><span style="color: #0000ff;">new</span><span style="color: #000000;"> LWordDBTask();<br>        </span><span style="color: #800080;">$dbTask</span><span style="color: #000000;">-></span><span style="color: #000000;">append(</span><span style="color: #800080;">$newLWord</span><span style="color: #000000;">);<br><br><span style="background-color: #e0e0e0;">        </span></span><span style="background-color: #e0e0e0;"><span style="color: #800080;">$ext</span><span style="color: #000000;">-></span><span style="color: #000000;">behindAppend(</span><span style="color: #800080;">$newLWord</span></span><span style="color: #000000;"><span style="background-color: #e0e0e0;">);</span><br>    }<br>};<br></span>
</div>
ログイン後にコピー

 

从代码10中可以看出虽然CheckPowerExtension、CheckContentExtension、AddScoreExtension以及LWordExtensionFamily都实现了ILWordExtension接口,但是它们的beforeAppend和behindAppend函数过程却完全不同!特别是LWordExtensionFamily扩展家族类,它并没有实质的业务逻辑处理过程,而是将调用依次传递给每一个扩展。beforeAppend和behindAppend函数在具体类中的不同实现,这是面向对象程序设计中的很典型的特性:多态!

 

将次业务逻辑分散到各个扩展中,这种做法已经非常近似AOP(Aspect OrientedProgramming,面向切面编程)的编程方式。权限校验、内容检查和积分可以看作是不同的切面,这些切面和主业务逻辑交叉在一起,但又不会影响到主业务逻……这样做的好处就是扩展代码不会干扰主业务逻辑,我们也可以针对某一个扩展进行编码和单元测试,然后通过MyExtensionFactory工厂类把扩展插入到业务流程中。完整的执行过程如图3所示:

 

このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。

ホットAIツール

Undresser.AI Undress

Undresser.AI Undress

リアルなヌード写真を作成する AI 搭載アプリ

AI Clothes Remover

AI Clothes Remover

写真から衣服を削除するオンライン AI ツール。

Undress AI Tool

Undress AI Tool

脱衣画像を無料で

Clothoff.io

Clothoff.io

AI衣類リムーバー

AI Hentai Generator

AI Hentai Generator

AIヘンタイを無料で生成します。

ホットツール

メモ帳++7.3.1

メモ帳++7.3.1

使いやすく無料のコードエディター

SublimeText3 中国語版

SublimeText3 中国語版

中国語版、とても使いやすい

ゼンドスタジオ 13.0.1

ゼンドスタジオ 13.0.1

強力な PHP 統合開発環境

ドリームウィーバー CS6

ドリームウィーバー CS6

ビジュアル Web 開発ツール

SublimeText3 Mac版

SublimeText3 Mac版

神レベルのコード編集ソフト(SublimeText3)

Ubuntu および Debian 用の PHP 8.4 インストールおよびアップグレード ガイド Ubuntu および Debian 用の PHP 8.4 インストールおよびアップグレード ガイド Dec 24, 2024 pm 04:42 PM

PHP 8.4 では、いくつかの新機能、セキュリティの改善、パフォーマンスの改善が行われ、かなりの量の機能の非推奨と削除が行われています。 このガイドでは、Ubuntu、Debian、またはその派生版に PHP 8.4 をインストールする方法、または PHP 8.4 にアップグレードする方法について説明します。

PHP 開発用に Visual Studio Code (VS Code) をセットアップする方法 PHP 開発用に Visual Studio Code (VS Code) をセットアップする方法 Dec 20, 2024 am 11:31 AM

Visual Studio Code (VS Code とも呼ばれる) は、すべての主要なオペレーティング システムで利用できる無料のソース コード エディター (統合開発環境 (IDE)) です。 多くのプログラミング言語の拡張機能の大規模なコレクションを備えた VS Code は、

今まで知らなかったことを後悔している 7 つの PHP 関数 今まで知らなかったことを後悔している 7 つの PHP 関数 Nov 13, 2024 am 09:42 AM

あなたが経験豊富な PHP 開発者であれば、すでにそこにいて、すでにそれを行っていると感じているかもしれません。あなたは、運用を達成するために、かなりの数のアプリケーションを開発し、数百万行のコードをデバッグし、大量のスクリプトを微調整してきました。

PHPでHTML/XMLを解析および処理するにはどうすればよいですか? PHPでHTML/XMLを解析および処理するにはどうすればよいですか? Feb 07, 2025 am 11:57 AM

このチュートリアルでは、PHPを使用してXMLドキュメントを効率的に処理する方法を示しています。 XML(拡張可能なマークアップ言語)は、人間の読みやすさとマシン解析の両方に合わせて設計された多用途のテキストベースのマークアップ言語です。一般的にデータストレージに使用されます

JSON Web Tokens(JWT)とPHP APIでのユースケースを説明してください。 JSON Web Tokens(JWT)とPHP APIでのユースケースを説明してください。 Apr 05, 2025 am 12:04 AM

JWTは、JSONに基づくオープン標準であり、主にアイデンティティ認証と情報交換のために、当事者間で情報を安全に送信するために使用されます。 1。JWTは、ヘッダー、ペイロード、署名の3つの部分で構成されています。 2。JWTの実用的な原則には、JWTの生成、JWTの検証、ペイロードの解析という3つのステップが含まれます。 3. PHPでの認証にJWTを使用する場合、JWTを生成および検証でき、ユーザーの役割と許可情報を高度な使用に含めることができます。 4.一般的なエラーには、署名検証障害、トークンの有効期限、およびペイロードが大きくなります。デバッグスキルには、デバッグツールの使用とロギングが含まれます。 5.パフォーマンスの最適化とベストプラクティスには、適切な署名アルゴリズムの使用、有効期間を合理的に設定することが含まれます。

母音を文字列にカウントするPHPプログラム 母音を文字列にカウントするPHPプログラム Feb 07, 2025 pm 12:12 PM

文字列は、文字、数字、シンボルを含む一連の文字です。このチュートリアルでは、さまざまな方法を使用してPHPの特定の文字列内の母音の数を計算する方法を学びます。英語の母音は、a、e、i、o、u、そしてそれらは大文字または小文字である可能性があります。 母音とは何ですか? 母音は、特定の発音を表すアルファベットのある文字です。大文字と小文字など、英語には5つの母音があります。 a、e、i、o、u 例1 入力:string = "tutorialspoint" 出力:6 説明する 文字列「TutorialSpoint」の母音は、u、o、i、a、o、iです。合計で6元があります

PHPでの後期静的結合を説明します(静的::)。 PHPでの後期静的結合を説明します(静的::)。 Apr 03, 2025 am 12:04 AM

静的結合(静的::) PHPで後期静的結合(LSB)を実装し、クラスを定義するのではなく、静的コンテキストで呼び出しクラスを参照できるようにします。 1)解析プロセスは実行時に実行されます。2)継承関係のコールクラスを検索します。3)パフォーマンスオーバーヘッドをもたらす可能性があります。

PHPマジックメソッド(__construct、__destruct、__call、__get、__setなど)とは何ですか? PHPマジックメソッド(__construct、__destruct、__call、__get、__setなど)とは何ですか? Apr 03, 2025 am 12:03 AM

PHPの魔法の方法は何ですか? PHPの魔法の方法には次のものが含まれます。1。\ _ \ _コンストラクト、オブジェクトの初期化に使用されます。 2。\ _ \ _リソースのクリーンアップに使用される破壊。 3。\ _ \ _呼び出し、存在しないメソッド呼び出しを処理します。 4。\ _ \ _ get、dynamic属性アクセスを実装します。 5。\ _ \ _セット、動的属性設定を実装します。これらの方法は、特定の状況で自動的に呼び出され、コードの柔軟性と効率を向上させます。

See all articles