The Memento design pattern without violating encapsulation, captures and externalizes an object‘s internal state so that the object can be restored to this state later.
A visualization of the classes and objects participating in this pattern.
The classes and objects participating in this pattern include:
Memento
)
SalesProspect
)
Caretaker
)
This structural code demonstrates the Memento pattern which temporary saves and restores another object's internal state.
using System;
namespace Memento.Structural
{
/// <summary>
/// Memento Design Pattern
/// </summary>
public class Program
{
public static void Main(string[] args)
{
Originator o = new Originator();
o.State = "On";
// Store internal state
Caretaker c = new Caretaker();
c.Memento = o.CreateMemento();
// Continue changing originator
o.State = "Off";
// Restore saved state
o.SetMemento(c.Memento);
// Wait for user
Console.ReadKey();
}
}
/// <summary>
/// The 'Originator' class
/// </summary>
public class Originator
{
string state;
public string State
{
get { return state; }
set
{
state = value;
Console.WriteLine("State = " + state);
}
}
// Creates memento
public Memento CreateMemento()
{
return (new Memento(state));
}
// Restores original state
public void SetMemento(Memento memento)
{
Console.WriteLine("Restoring state...");
State = memento.State;
}
}
/// <summary>
/// The 'Memento' class
/// </summary>
public class Memento
{
string state;
// Constructor
public Memento(string state)
{
this.state = state;
}
public string State
{
get { return state; }
}
}
/// <summary>
/// The 'Caretaker' class
/// </summary>
public class Caretaker
{
Memento memento;
public Memento Memento
{
set { memento = value; }
get { return memento; }
}
}
}
This real-world code demonstrates the Memento pattern which temporarily saves and then restores the SalesProspect's internal state.
using System;
namespace Memento.RealWorld
{
/// <summary>
/// Memento Design Pattern
/// </summary>
public class Program
{
public static void Main(string[] args)
{
SalesProspect s = new SalesProspect();
s.Name = "Noel van Halen";
s.Phone = "(412) 256-0990";
s.Budget = 25000.0;
// Store internal state
ProspectMemory m = new ProspectMemory();
m.Memento = s.SaveMemento();
// Continue changing originator
s.Name = "Leo Welch";
s.Phone = "(310) 209-7111";
s.Budget = 1000000.0;
// Restore saved state
s.RestoreMemento(m.Memento);
// Wait for user
Console.ReadKey();
}
}
/// <summary>
/// The 'Originator' class
/// </summary>
public class SalesProspect
{
string name;
string phone;
double budget;
// Gets or sets name
public string Name
{
get { return name; }
set
{
name = value;
Console.WriteLine("Name: " + name);
}
}
// Gets or sets phone
public string Phone
{
get { return phone; }
set
{
phone = value;
Console.WriteLine("Phone: " + phone);
}
}
// Gets or sets budget
public double Budget
{
get { return budget; }
set
{
budget = value;
Console.WriteLine("Budget: " + budget);
}
}
// Stores memento
public Memento SaveMemento()
{
Console.WriteLine("\nSaving state --\n");
return new Memento(name, phone, budget);
}
// Restores memento
public void RestoreMemento(Memento memento)
{
Console.WriteLine("\nRestoring state --\n");
Name = memento.Name;
Phone = memento.Phone;
Budget = memento.Budget;
}
}
/// <summary>
/// The 'Memento' class
/// </summary>
public class Memento
{
string name;
string phone;
double budget;
// Constructor
public Memento(string name, string phone, double budget)
{
this.name = name;
this.phone = phone;
this.budget = budget;
}
public string Name
{
get { return name; }
set { name = value; }
}
public string Phone
{
get { return phone; }
set { phone = value; }
}
public double Budget
{
get { return budget; }
set { budget = value; }
}
}
/// <summary>
/// The 'Caretaker' class
/// </summary>
public class ProspectMemory
{
Memento memento;
public Memento Memento
{
set { memento = value; }
get { return memento; }
}
}
}
The .NET optimized code demonstrates the
same real-world situation as above but uses modern, built-in .NET features,
such as, generics, reflection, LINQ, lambda functions, etc.
You can find an example on our Singleton pattern page.
All other patterns (and much more) are available in our Dofactory .NET product.
Not only does Dofactory .NET cover the Gang of Four and Enterprise patterns, it also includes
pattern architectures, low-code, and RAD (Rapid Application Development) techniques.
Accelerate development to where you can write
entire solutions in just 33 days!.
This unique package will change your developer lifestyle.
Here's what is included: