<span><span><?php </span></span><span><span>public class User </span></span><span><span>{ </span></span><span> <span>public function borrowBook() { </span></span><span> <span>$bookManager = new Book_Manager(); </span></span><span> <span>$bookManager->returnBooks(); </span></span><span> </span><span> <span>$bookPayments = new Book_Payments(); </span></span><span> <span>if ($bookPayments->hasOverdueBooks()) { </span></span><span> <span>$bookPayments->payBookFines(); </span></span><span> <span>} </span></span><span> </span><span> <span>$bookLibrary = new Book_Library(); </span></span><span> <span>$bookReservations = new Book_Reservations(); </span></span><span> </span><span> <span>$book = $bookLibrary->searchBooks(); </span></span><span> <span>$isAvailable = $bookLibrary->isBookAvailable($book); </span></span><span> <span>$isReserved = $bookReservations->isBookReserved($book); </span></span><span> <span>if ($isAvailable && !isReserved) { </span></span><span> <span>$bookLibrary->locateBook($book); </span></span><span> </span><span> <span>$bookManager->borrowBook($book); </span></span><span> <span>$bookLibrary->updateBookAvailability($book, $status); </span></span><span> <span>} </span></span><span> <span>} </span></span><span><span>}</span></span>您可以看到借書的過程實際上是一個複雜的過程!在此實施中,用戶必須與四個不同類別和大約十種方法進行交互才能藉書。 假設每個功能都被用作應用程序中的單獨屏幕。您能想像使用該系統藉三本書所需的努力嗎?借款人不需要了解諸如檢查預訂和更新狀態之類的功能。我們的實施肯定有問題。
<span><span><?php </span></span><span><span>class Library_Facade </span></span><span><span>{ </span></span><span> <span>public function returnBooks() { </span></span><span> <span>// previous implementation by calling necessary classes </span></span><span> <span>} </span></span><span> </span><span> <span>public function borrowBooks() { </span></span><span> <span>} </span></span><span> </span><span> <span>public function searchBooks() { </span></span><span> <span>} </span></span><span> </span><span> <span>public function reserveBooks() { </span></span><span> <span>} </span></span><span><span>}</span></span>用戶可以通過調用brownbook()庫庫facade類的方法借入書籍,如下所示:
<span><span><?php </span></span><span><span>class User </span></span><span><span>{ </span></span><span> <span>public function borrowBook() { </span></span><span> <span>$libraryFacade = new Library_Facade(); </span></span><span> <span>$libraryFacade->borrowBook(); </span></span><span> <span>} </span></span><span><span>}</span></span>借助此基於立體的實現,用戶僅與Library_facade類對話,並且不知道該功能是如何實現的。用戶可以直接從立面上索取任何功能,外牆負責處理複雜過程並返回適當的信息。立面模式遵守每個單元應對其他單位具有最低知識的知識的原則。 即使低級功能通過外牆隱藏在用戶中,用戶仍然可以在需要時直接請求低級類。考慮一下自己的項目,以及您可能在沒有意識到的情況下找到實現立面模式的情況。
>外觀是一個對象,它為較大的代碼(例如類庫)提供簡化的接口。立面可以:>
- 使軟件庫更易於使用,理解和測試,因為立面具有方便的常見任務方法; 出於相同的原因,
使庫更易讀;- >
>減少庫內部工作的外部代碼的依賴關係,因為大多數代碼都使用該立面在開發系統時更靈活;- 包裹一個設計良好的API集合,具有一個精心設計的API。 這是我們庫示例的類圖,該示例標識了立面模式定義中提到的組件。
現實世界實施
在前面的部分中,我們以圖書館系統為例了解了立面模式背後的理論。在現實世界中,立面可能比我們圖書館場景中的實施更為複雜。讓我們回顧一下現實應用程序和庫中該模式的一些實現。opauth用於打開身份驗證
我最近寫了一篇有關一個流行的公開身份驗證庫的文章,稱為Opauth,建議您閱讀,如果您還沒有閱讀。假設我們已經開發了一個專業的社交網站,希望我們的用戶能夠使用其他受歡迎的網站,例如Twitter,LinkedIn和Facebook進行身份驗證。為了完成身份驗證過程,我們使用現有的第三方庫來訪問網絡的服務。讓我們看一些帶有Twitter庫的示例代碼,以實現所需的功能。<span><span><?php </span></span><span><span>public class User </span></span><span><span>{ </span></span><span> <span>public function borrowBook() { </span></span><span> <span>$bookManager = new Book_Manager(); </span></span><span> <span>$bookManager->returnBooks(); </span></span><span> </span><span> <span>$bookPayments = new Book_Payments(); </span></span><span> <span>if ($bookPayments->hasOverdueBooks()) { </span></span><span> <span>$bookPayments->payBookFines(); </span></span><span> <span>} </span></span><span> </span><span> <span>$bookLibrary = new Book_Library(); </span></span><span> <span>$bookReservations = new Book_Reservations(); </span></span><span> </span><span> <span>$book = $bookLibrary->searchBooks(); </span></span><span> <span>$isAvailable = $bookLibrary->isBookAvailable($book); </span></span><span> <span>$isReserved = $bookReservations->isBookReserved($book); </span></span><span> <span>if ($isAvailable && !isReserved) { </span></span><span> <span>$bookLibrary->locateBook($book); </span></span><span> </span><span> <span>$bookManager->borrowBook($book); </span></span><span> <span>$bookLibrary->updateBookAvailability($book, $status); </span></span><span> <span>} </span></span><span> <span>} </span></span><span><span>}</span></span>如您所見,我們調用一組特定於Twitter的庫方法來實現所需的功能。 LinkedIn和Facebook都需要類似的方法。該過程已經變得複雜。我們沒有開發Twitter,Facebook或LinkedIn應用程序;我們應該只驗證憑據並驗證用戶。我們的應用程序不必擔心這些服務的實施。 我們可以通過使用Opauth庫作為立面接口來解決此問題。首先,我們需要以通用格式指定所需服務的登錄URL,以通過Opauth插件標識。考慮以下用於實施身份驗證過程的代碼。<span><span><?php </span></span><span><span>class Library_Facade </span></span><span><span>{ </span></span><span> <span>public function returnBooks() { </span></span><span> <span>// previous implementation by calling necessary classes </span></span><span> <span>} </span></span><span> </span><span> <span>public function borrowBooks() { </span></span><span> <span>} </span></span><span> </span><span> <span>public function searchBooks() { </span></span><span> <span>} </span></span><span> </span><span> <span>public function reserveBooks() { </span></span><span> <span>} </span></span><span><span>}</span></span>一旦請求登錄鏈接,Opauth就會從URL標識所請求的服務,並初始化庫以重定向用戶進行身份驗證。現在,我們的應用程序只需要創建登錄鏈接並調用初始化方法。所有復雜的身份驗證內容均使用每個服務的各個庫來處理幕後。這可以被認為是有效使用立面模式的完美示例。WordPress meta函數
考慮到其代碼的質量,WordPress並不是嚴重的PHP開發人員中最受歡迎的框架之一。但是我們可以輕鬆地在WordPress代碼庫中找到許多成功的立面實現。在這裡,我將查看update_post_meta()函數,以保存WordPress帖子的自定義數據。 WordPress允許我們創建與現有帖子關聯的自定義字段。考慮一下我們如何在通常情況下保存這些領域……我們必須執行以下所有任務:保存一個自定義字段的工作是很多工作! WordPress通過提供稱為update_post_meta()的內置功能來隱藏保存這些字段的複雜性 充當立面。這使我們能夠專注於傳遞與應用程序相關的必要數據;所有上述任務都隱藏在用戶中。 現在,考慮實現Update_post_meta()以將其功能識別為立面:
- 驗證字段數據
- >過濾HTML標籤,腳本和SQL注入的數據
- 檢查數據庫中的字段的存在
- >根據存在狀態
保存或更新記錄<span><span><?php </span></span><span><span>public class User </span></span><span><span>{ </span></span><span> <span>public function borrowBook() { </span></span><span> <span>$bookManager = new Book_Manager(); </span></span><span> <span>$bookManager->returnBooks(); </span></span><span> </span><span> <span>$bookPayments = new Book_Payments(); </span></span><span> <span>if ($bookPayments->hasOverdueBooks()) { </span></span><span> <span>$bookPayments->payBookFines(); </span></span><span> <span>} </span></span><span> </span><span> <span>$bookLibrary = new Book_Library(); </span></span><span> <span>$bookReservations = new Book_Reservations(); </span></span><span> </span><span> <span>$book = $bookLibrary->searchBooks(); </span></span><span> <span>$isAvailable = $bookLibrary->isBookAvailable($book); </span></span><span> <span>$isReserved = $bookReservations->isBookReserved($book); </span></span><span> <span>if ($isAvailable && !isReserved) { </span></span><span> <span>$bookLibrary->locateBook($book); </span></span><span> </span><span> <span>$bookManager->borrowBook($book); </span></span><span> <span>$bookLibrary->updateBookAvailability($book, $status); </span></span><span> <span>} </span></span><span> <span>} </span></span><span><span>}</span></span>僅顯示必要的代碼; update_metadata()函數的完整源代碼可在wp-rudes目錄內的meta.php文件中找到。但是,您可以在此處看到所有驗證,過濾和數據庫更新,並且只有立面界面才有有關詳細信息的知識。結論
立面是軟件開發中最簡單,最易於使用的設計模式之一。在本文中,我討論了外牆模式的各種實現。現在是時候在下面的評論中分享您的經驗了。您知道使用外牆的圖書館或服務嗎?隨意分享您遇到的立面模式的實際實現。 通過fotolia 圖像 經常詢問有關立面模式的問題>
>軟件設計中立面模式的主要目的是什麼?> >外牆模式是一種結構設計模式,可為複雜的類,庫或框架系統提供簡化的接口。它隱藏了系統的複雜性,並從客戶端可以訪問系統的地方為客戶端提供了一個接口。該模式涉及一個單一類,該類提供客戶端要求的簡化方法,並代表呼叫對現有系統類的方法的調用。
如何改善代碼可讀性和可用性?通過為複雜子系統提供簡單的接口來改善代碼的可讀性和可用性。該立面沒有直接與幾個子系統類打交道,而是用統一接口封裝了子系統。這減少了了解子系統所需的學習曲線,並使子系統更易於使用和管理。
您可以提供立面模式的真實示例嗎?
外牆模式的使用是使用計算機。打開計算機時,您無需了解內部組件如何共同啟動系統。您只需按下電源按鈕(立面),複雜的過程發生在幕後。
使用立面模式的優點和缺點是什麼?
>
>立面模式的主要優點是,它簡化了複雜子系統的接口,從而使客戶端更容易使用。它還促進了子系統與其客戶之間的脫鉤,這可以使系統更易於模塊化和更易於維護。但是,潛在的劣勢是,如果在外牆中放置過多的功能,立面模式可能會成為瓶頸。它還可以從客戶端隱藏子系統的有用功能。>
與其他結構設計模式有何不同?>與其他結構設計模式不同,例如適配器或裝飾器模式,哪些結構設計模式(用於添加或更改單個對象的行為,立面模式用於簡化複雜的類系統。它提供了一個複雜子系統的簡化接口,將子系統的複雜性隱藏在客戶端中。
可以將立面模式與其他設計模式一起使用嗎?與其他設計模式結合使用。例如,它可以與Singleton模式一起使用,以確保僅創建一個立面實例。它也可以與抽象的工廠模式一起使用,以提供一個簡單的接口來創建相關對象的家族。
> 如何有助於最少知識的原理?通過限制對象之間的溝通來促進最少知識(或Demeter定律)的原則。客戶只需要與外牆進行通信,而不是與子系統類通信。這樣可以降低對象之間的依賴項,從而使系統更穩固,更易於維護。可以在多線程應用程序中使用外觀模式嗎?多線程應用程序。但是,必須注意確保立面是線程安全的。這可以通過使用鎖或信號量等同步機制來防止比賽條件來實現這一點。>
如何影響表面模式? >客戶需要與之互動。這可以減少對象創建和方法調用的開銷。但是,如果立面變成瓶頸,它可能會對性能產生負面影響。
>>我如何在PHP中實現立面模式?提供複雜子系統的簡化接口的立麵類。立麵類應封裝子系統,並將呼籲召集到子系統類。客戶應通過立面與子系統互動,而不是直接與子系統類交互。
以上是PHP主|通過立面模式管理複雜性的詳細內容。更多資訊請關注PHP中文網其他相關文章!