PHP單一職責原則(SRP)使用案例解析
這次帶給大家PHP單一職責原則(SRP)使用案例解析,PHP單一職責原則(SRP)使用的注意事項有哪些,以下就是實戰案例,一起來看一下。
單一職責原則(Single Pesponsibility Principle, SRP)
單一職責有兩個意義: 一個是避免相同的職責分散到不同的類別中, 別一個是避免一個類別承擔太多職責
為什麼要遵守SRP呢?
(1)可以減少類別之間的耦合
如果減少類別之間的耦合,當需求變化時,只修改一個類,從而也就隔離了變化;如果一個類別有多個不同職責,它們耦合在一起,當一個職責發生變化時,可能會影響到其他職責。
(2)提高類別的複用性
修改電腦比修理電視機簡單多了。主要原因就在於電視機各個部件之間的耦合性太高,而電腦則不同,電腦的內存、硬碟、音效卡、網卡、鍵盤燈等部件都可以輕鬆地單獨拆卸和組裝。某個部件壞了,換上新的即可。上面的例子就體現了單一職責的優勢。由於使用了單一職責,使得‘組件'可以方便地‘拆卸’和‘組裝’。
不遵守SRP會影響對類別的複用性。當只需要用該類別的某一個職責時,由於它和其他的職責耦合在一起,也就很難分離出。
遵守SRP在實際程式碼開發上有沒有什麼應用?有的。以資料持久層為例,所謂的資料持久層主要指的是資料庫操作,當然,也包含快取管理等。這時就需要資料持久層支援多種資料庫。應該怎麼做?定義多個資料庫操作類別?想法已經很接近了,再進一步,就是使用工廠模式。
工廠模式(Faction)允許你在程式碼執行時實例化物件。它之所以被稱為工廠模式是因為它負責『生產對象』。以資料庫為例,工廠需要的就是根據不同的參數,產生不同的實例化物件。最簡單的工廠就是根據傳入的型別名稱實例化對象,如傳入MySQL,就呼叫MySQL類別並實例化,如果是SQLite,則呼叫SQLite的類別並實例化,甚至還可以處理TXT、Execl等'類資料庫'。
工廠類也就是這樣的一個類,它只負責生產對象,而不負責對象的具體內容。
以下是範例
定義一個適配器的介面
interface Db_Adpater { /** * 数据库连接 * @param $config 数据库配置 * @return mixed resource */ public function connect($config); /** * 执行数据库查询 * @param $query 数据库查询的SQL字符串 * @param $handle 连接对象 * @return mixed */ public function query($query,$handle); }
定義一個實作了DB_Adpater介面的MySQL資料庫操作類
class Db_Adapter_Mysql implements Db_Adpater { private $_dbLink; //数据库连接字符串标识 /** * 数据库连接函数 * @param $config 数据库配置 * @return resource * @throws Db_Exception */ public function connect($config) { if($this->_dbLink = @mysql_connect($config->host . (empty($config->port) ? '' : ':' . $config->prot) ,$config->user, $config->password, true)) { if(@mysql_select_db($config->database, $this->_dbLink)) { if($config->charset) { mysql_query("SET NAME '{$config->charset}'", $this->_dbLink); } return $this->_dbLink; } } throw new Db_Exception(@mysql_error($this->_dbLink)); } /** * 执行数据库查询 * @param $query 数据库查询SQL字符串 * @param $handle 连接对象 * @return resource */ public function query($query,$handle) { if($resource = @mysql_query($query,$handle)) return $resource; } }
定義一個實現了DB_Adpater介面的SQLite資料庫操作類
class Db_Adapter_sqlite implements Db_Adpater { private $_dbLink; //数据库连接字符串标识 public function connect($config) { if($this->_dbLink = sqlite_open($config->file, 0666, $error)) { return $this->_dbLink; } throw new Db_Exception($error); } public function query($query, $handle) { if($resource = @sqlite_query($query,$handle)) { return $resource; } } }
現在如果需要一個資料庫操作的方法怎麼做,只需定義一個工廠類,根據傳入不同的生成需要的類別即可
class sqlFactory { public static function factory($type) { if(include_once 'Drivers/' . $type . '.php') { $classname = 'Db_Adapter_'.$type; return new $classname; } else throw new Exception('Driver not found'); } }
呼叫時,就可以這麼寫
$db = sqlFactory::factory('MySQL'); $db = sqlFactory::factory('SQLite');
我們把建立資料庫連接這塊程式單獨拿出來,程式中的CURD就不用關心什麼資料庫了,只要依照規範使用對應的方法即可。
工廠方法讓具體的物件解脫出來,使其不再依賴具體的類,而是抽象化。
設計模式裡面的命令模式也是SRP的體現,命令模式分離「命令的請求者」和「命令的實現者」方面的職責。舉一個很好理解的例子,就是你去餐廳訂餐吃飯,餐廳有顧客、服務生、廚師三個角色。作為顧客,你要列出菜單,傳給服務員,由服務員通知廚師去實現。身為服務員,只要呼叫準備飯菜這個方法(對著廚師喊著「該炒菜了」),廚師聽到要炒菜的請求,就立刻去煮飯。在這裡,命令的請求和實作就完成了解耦。
模擬這個過程,先定義廚師角色,廚師進行實際煮飯、燒湯的工作。
以下是範例
/** * 厨师类,命令接受者与执行者 * Class cook */ class cook { public function meal() { echo '番茄炒鸡蛋',PHP_EOL; } public function drink() { echo '紫菜蛋花汤',PHP_EOL; } public function ok() { echo '完毕',PHP_EOL; } } //然后是命令接口 interface Command { public function execute(); }
輪到服務生出場,服務生是指令的傳送者,通常你到飯館吃飯都是叫服務生吧,不能直接叫廚師,一般都是叫「服務生,給我來盤番茄炒西紅柿」。所以,服務生是顧客和廚師之間的命令溝通都。
class MealCommand implements Command { private $cook; //绑定命令接受者 public function construct(cook $cook) { $this->cook = $cook; } public function execute() { $this->cook->meal();//把消息传给厨师,让厨师做饭,下同 } } class DrinkCommand implements Command { private $cook; //绑定命令接受者 public function construct(cook $cook) { $this->cook = $cook; } public function execute() { $this->cook->drink(); } }
現在顧客可以依照選單叫服務生了
class cookControl { private $mealcommand; private $drinkcommand; //将命令发送者绑定以命令接收器上面来 public function addCommand(Command $mealcommand, Command $drinkcommand) { $this->mealcommand = $mealcommand; $this->drinkcommand = $drinkcommand; } public function callmeal() { $this->mealcommand->execute(); } public function calldrink() { $this->drinkcommand->execute(); } }
好了,现在完成整个过程
$control = new cookControl; $cook = new cook; $mealcommand = new MealCommand($cook); $drinkcommand = new DrinkCommand($cook); $control->addCommand($mealcommand,$drinkcommand); $control->callmeal(); $control->calldrink();
从上面的例子可以看出,原来设计模式并非纯理论的东西,而是来源于实际生活,就连普通的餐馆老板都懂设计模式这门看似高深的学问。其实,在经济和管理活动中对流程的优化就是对各种设计模式的摸索和实践。所以,设计模式并非计算机编程中的专利。事实上,设计模式的起源并不是计算机,而是源于建筑学。
在设计模式方面,不仅以上这两种体现了SRP,还有别的(比如代理模式)也体现了SRP。SRP不只是对类设计有意义,对以模块、子系统为单位的系统架构设计同样有意义。
模块、子系统也应该仅有一个引起它变化的原因,如MVC所倡导的各个层之间的相互分离就是SRP在系统总体设计中的应用。
SRP是最简单的原则之一,也是最难做好的原则之一。我们会很自然地将职责连接在一起。找到并且分离这些职责是软件设计需要达到的目的
一些简单的应用遵循的做法如下:
根据业务流程,把业务对象提炼出来。如果业务的流程的链路太复杂,就把这个业务对象分离为多个单一业务对象。当业务链标准化后,对业务对象的内部情况做进一步处理,把第一次标准化视为最高层抽象,第二次视为次高层抽象,以此类推,直到“恰如其分”的设计层次
职责的分类需要注意。有业务职责,还要有脱离业务的抽象职责,从认识业务到抽象算法是一个层层递进的过程。就好比命令模式中的顾客,服务员和厨师的职责,作为老板(即设计师)的你需要规划好各自的职责范围,即要防止越俎代庖,也要防止互相推诿。
相信看了本文案例你已经掌握了方法,更多精彩请关注php中文网其它相关文章!
推荐阅读:
以上是PHP單一職責原則(SRP)使用案例解析的詳細內容。更多資訊請關注PHP中文網其他相關文章!

熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

Video Face Swap
使用我們完全免費的人工智慧換臉工具,輕鬆在任何影片中換臉!

熱門文章

熱工具

記事本++7.3.1
好用且免費的程式碼編輯器

SublimeText3漢化版
中文版,非常好用

禪工作室 13.0.1
強大的PHP整合開發環境

Dreamweaver CS6
視覺化網頁開發工具

SublimeText3 Mac版
神級程式碼編輯軟體(SublimeText3)

PHP 8.4 帶來了多項新功能、安全性改進和效能改進,同時棄用和刪除了大量功能。 本指南介紹如何在 Ubuntu、Debian 或其衍生版本上安裝 PHP 8.4 或升級到 PHP 8.4

本教程演示瞭如何使用PHP有效地處理XML文檔。 XML(可擴展的標記語言)是一種用於人類可讀性和機器解析的多功能文本標記語言。它通常用於數據存儲

JWT是一種基於JSON的開放標準,用於在各方之間安全地傳輸信息,主要用於身份驗證和信息交換。 1.JWT由Header、Payload和Signature三部分組成。 2.JWT的工作原理包括生成JWT、驗證JWT和解析Payload三個步驟。 3.在PHP中使用JWT進行身份驗證時,可以生成和驗證JWT,並在高級用法中包含用戶角色和權限信息。 4.常見錯誤包括簽名驗證失敗、令牌過期和Payload過大,調試技巧包括使用調試工具和日誌記錄。 5.性能優化和最佳實踐包括使用合適的簽名算法、合理設置有效期、

靜態綁定(static::)在PHP中實現晚期靜態綁定(LSB),允許在靜態上下文中引用調用類而非定義類。 1)解析過程在運行時進行,2)在繼承關係中向上查找調用類,3)可能帶來性能開銷。

字符串是由字符組成的序列,包括字母、數字和符號。本教程將學習如何使用不同的方法在PHP中計算給定字符串中元音的數量。英語中的元音是a、e、i、o、u,它們可以是大寫或小寫。 什麼是元音? 元音是代表特定語音的字母字符。英語中共有五個元音,包括大寫和小寫: a, e, i, o, u 示例 1 輸入:字符串 = "Tutorialspoint" 輸出:6 解釋 字符串 "Tutorialspoint" 中的元音是 u、o、i、a、o、i。總共有 6 個元

PHP的魔法方法有哪些? PHP的魔法方法包括:1.\_\_construct,用於初始化對象;2.\_\_destruct,用於清理資源;3.\_\_call,處理不存在的方法調用;4.\_\_get,實現動態屬性訪問;5.\_\_set,實現動態屬性設置。這些方法在特定情況下自動調用,提升代碼的靈活性和效率。

PHP和Python各有優勢,選擇依據項目需求。 1.PHP適合web開發,尤其快速開發和維護網站。 2.Python適用於數據科學、機器學習和人工智能,語法簡潔,適合初學者。

PHP是一種廣泛應用於服務器端的腳本語言,特別適合web開發。 1.PHP可以嵌入HTML,處理HTTP請求和響應,支持多種數據庫。 2.PHP用於生成動態網頁內容,處理表單數據,訪問數據庫等,具有強大的社區支持和開源資源。 3.PHP是解釋型語言,執行過程包括詞法分析、語法分析、編譯和執行。 4.PHP可以與MySQL結合用於用戶註冊系統等高級應用。 5.調試PHP時,可使用error_reporting()和var_dump()等函數。 6.優化PHP代碼可通過緩存機制、優化數據庫查詢和使用內置函數。 7
