标签:
原文:C#设计模式(23)——备忘录模式(Memento Pattern)一、引言
在上一篇博文分享了访谒者模式,访谒者模式的实现是把感化于某种数据布局上的操纵封装到访谒者中,使得操纵和数据布局断绝。现在天要介绍的备忘者模式与命令模式有点相似,差此外是,命令模式生存的是倡议人的具体命令(命令对应的是行为),而备忘录模式生存的是倡议人的状态(而状态对应的数据布局,如属性)。下面具体来看看备忘录模式。
二、备忘录模式介绍 2.1 备忘录模式的界说从字面意思就可以大白,,备忘录模式就是对某个类的状态进行生存下来,等到需要恢复的时候,可以从备忘录中进行恢复。生活中这样的例子经常看到,如备忘电话通讯录,备份操纵操纵系统,备份数据库等。
备忘录模式的具体界说是:在不粉碎封装的前提下,捕获一个东西的内部状态,并在该东西之外生存这个状态,这样以后就可以把该东西恢复到原先的状态。
2.2 备忘录模式的布局图介绍完备忘录模式的界说之后,下面具体看看备忘录模式的布局图:
备忘录模式中主要有三类角色:
倡议人角色:记录当前时刻的内部状态,卖力创建和恢复备忘录数据。
备忘录角色:卖力存储倡议人东西的内部状态,在进行恢复时供给给倡议人需要的状态。
打点者角色:卖力生存备忘录东西。
2.3 备忘录模式的实现下面以备份手机通讯录为例子来实现了备忘录模式,具体的实现代码如下所示:
// 联系人 public class ContactPerson { public string Name { get; set; } public string MobileNum { get; set; } } // 倡议人 public class MobileOwner { // 倡议人需要生存的内部状态 public List<ContactPerson> ContactPersons { get; set; } public MobileOwner(List<ContactPerson> persons) { ContactPersons = persons; } // 创建备忘录,将当期要生存的联系人列表导入到备忘录中 public ContactMemento CreateMemento() { // 这里也应该通报深拷贝,new List方法通报的是浅拷贝, // 因为ContactPerson类中都是string类型,所以这里new list方法对ContactPerson东西执行了深拷贝 // 如果ContactPerson包孕非string的引用类型就会有问题,所以这里也应该用序列化通报深拷贝 return new ContactMemento(new List<ContactPerson>(this.ContactPersons)); } // 将备忘录中的数据备份导入到联系人列表中 public void RestoreMemento(ContactMemento memento) { // 下面这种方法是错误的,因为这样通报的是引用, // 则删除一次可以恢复,但恢复之后再删除的话就恢复不了. // 所以应该通报contactPersonBack的深拷贝,深拷贝可以使用序列化来完成 this.ContactPersons = memento.contactPersonBack; } public void Show() { Console.WriteLine("联系人列表中有{0}小我私家,他们是:", ContactPersons.Count); foreach (ContactPerson p in ContactPersons) { Console.WriteLine("姓名: {0} 号码为: {1}", p.Name, p.MobileNum); } } } // 备忘录 public class ContactMemento { // 生存倡议人的内部状态 public List<ContactPerson> contactPersonBack; public ContactMemento(List<ContactPerson> persons) { contactPersonBack = persons; } } // 打点角色 public class Caretaker { public ContactMemento ContactM { get; set; } } class Program { static void Main(string[] args) { List<ContactPerson> persons = new List<ContactPerson>() { new ContactPerson() { Name= "Learning Hard", MobileNum = "123445"}, new ContactPerson() { Name = "Tony", MobileNum = "234565"}, new ContactPerson() { Name = "Jock", MobileNum = "231455"} }; MobileOwner mobileOwner = new MobileOwner(persons); mobileOwner.Show(); // 创建备忘录并生存备忘录东西 Caretaker caretaker = new Caretaker(); caretaker.ContactM = mobileOwner.CreateMemento(); // 变动倡议人联系人列表 Console.WriteLine("----移除最后一个联系人--------"); mobileOwner.ContactPersons.RemoveAt(2); mobileOwner.Show(); // 恢复到原始状态 Console.WriteLine("-------恢复联系人列表------"); mobileOwner.RestoreMemento(caretaker.ContactM); mobileOwner.Show(); Console.Read(); } }
具体的运行功效如下图所示: