好幾天沒寫部落格了,前幾天在網上看到一個設計模式叫做備忘錄模式。覺得還是比較有趣,自己寫了個模仿電腦備份的小例子。先看下備忘錄模式的介紹吧
備忘錄模式(Memento Pattern)又叫做快照模式(Snapshot Pattern)或Token模式,是GoF的23種設計模式之一,屬於行為模式。 定義(源於GoF《設計模式》):在不破壞封閉的前提下,捕獲一個對象的內部狀態,並在該對象之外儲存這個狀態。這樣以後就可將該對象恢複到原先儲存的狀態。 涉及角色: 1.Originator(發起人):負責建立一個備忘錄Memento,用以記錄當前時刻自身的內部狀態,並可使用備忘錄恢複內部狀態。 Originator可以根據需要決定Memento儲存自己的哪些內部狀態。 2.Memento(備忘錄):負責儲存Originator對象的內部狀態,並可以防止Originator以外的其他對象訪問備忘錄。備忘錄有兩個介面:Caretaker只能看到備忘錄的窄介面,他只能將備忘錄傳遞給其他對象。Originator卻可看到備忘錄的寬介面,允許它訪問返回到先前狀態所需要的所有資料。 3.Caretaker(管理者):負責備忘錄Memento, 不能對Memento的內容進行訪問或者操作。 備忘錄模式的優點和缺點 一、備忘錄模式的優點 1、有時一些發起人對象的內部資訊必須儲存在發起人對象以外的地方,但是必須要由發起人對象自己讀取,這時, 使用備忘錄模式可以把複雜的發起人內部資訊對其他的對象屏蔽起來,從而可以 恰當地保持封裝的邊界。 2、本模式簡化了發起人類。發起人不再需要管理和儲存其內部狀態的一個個版本,用戶端可以自行管理他們所需 要的這些狀態的版本。 3、當發起人角色的狀態改變的時候,有可能這個狀態無效,這時候就可以使用暫時儲存起來的備忘錄將狀態複原。 二、備忘錄模式的缺點: 1、如果發起人角色的狀態需要完整地儲存到備忘錄對象中,那麼在資源消耗上面備忘錄對象會很昂貴。 2、當負責人角色將一個備忘錄 儲存起來的時候,負責人可能並不知道這個狀態會佔用多大的儲存空間,從而無法提醒使用者一個操作是否很昂貴。 3、當發起人角色的狀態改變的時候,有可能這個協議無效。如果狀態改變的成功率不高的話,不如採取“假如”協議模式。
下面就上一個我寫的例子
1.備忘錄類
using System;using System.Collections.Generic;using System.Linq;using System.Text;namespace Recover.org.lxh{ //備忘錄角色 public class Memento { private string status; public string Status { get { return status; } set { Console.WriteLine("系統處於:"+this.status); status = value; } } public Memento(string status) { this.status = status; } }}
2.發起人類
using System;using System.Collections.Generic;using System.Linq;using System.Text;namespace Recover.org.lxh{ //發起人 public class WindowsSystem { private string status; public string Status { get { return status; } set { status = value; } } public Memento createOtherSystem() { return new Memento(status); } public void recoverSystem(Memento m) { this.status = m.Status; } }}
3.負責人(備忘錄管理者)
using System;using System.Collections.Generic;using System.Linq;using System.Text;namespace Recover.org.lxh{ //負責人(備忘錄管理者) public class UserComputer { private Memento memento; public Memento recoverMemento() { // 恢複系統 return this.memento; } public void createMemento(Memento memento) { // 儲存系統 this.memento = memento; } }}
4.測試類別
using System;using System.Collections.Generic;using System.Linq;using System.Text;using Recover.org.lxh;namespace Recover{ class Program { static void Main(string[] args) { WindowsSystem Winxp = new WindowsSystem(); // Winxp系統 UserComputer user = new UserComputer(); // 某一使用者 Winxp.Status="好的狀態"; // Winxp處於好的運行狀態 user.createMemento(Winxp.createOtherSystem()); // 使用者對系統進行備份,Winxp系統要產生備份檔案 Winxp.Status="壞的狀態"; // Winxp處於不好的運行狀態 Winxp.recoverSystem(user.recoverMemento()); // 使用者發恢複命令,系統進行恢複 Console.WriteLine("當前系統處於" + Winxp.Status); Console.ReadKey(); } }}