Memento

Structural example

#include <iostream>
#include <string>
using namespace std;
 
 
class Memento {
private:
	string _state;
protected:
	friend class Originator;
	Memento(const string &state) {
		_state = state;
	}
	// Gets or sets state
	string getState() {
		return _state;
	}
};
 
 
class Originator {
private:
	string _state;
public:
	// Property
	string getState() {
		return _state;
	}
	void setState(const string &value) {
		_state = value;
		cout << "State = " << _state << endl;
	}
	// Creates memento
	Memento* CreateMemento() {
		return new Memento(_state);
	}
	// Restores original state
	void SetMemento(Memento *memento) {
		cout << "Restoring state..." << endl;
		setState(memento->getState());
	}
};
 
 
class Caretaker {
private:
	Memento *_memento;
public:
	Caretaker() {
		_memento = NULL;
	}
	~Caretaker() {
		if (_memento != NULL) {
			delete _memento;
		}
	}
	void setMemento(Memento *memento) {
		_memento = memento;
	}
	Memento* getMemento() {
		return _memento;
	}
};
 
 
 
////////
int main() {
	Originator *o = new Originator;
	o->setState("ON");
 
	// Store internal state
	Caretaker *c = new Caretaker;
	c->setMemento(o->CreateMemento());
 
	// Continue changing originator
	o->setState("OFF");
 
	// Restore saved state
	o->SetMemento(c->getMemento());
 
	delete c;
	delete o;
	return 0;
}
 


Real World example

#include <iostream>
#include <string>
using namespace std;
 
// The 'Memento' class
class Memento {
private:
	string _name;
	string _phone;
	double _budget;
public:
	friend class SalesProspect;
	// Constructor
	Memento(const string &name, const string &phone, double budget) {
		_name = name;
		_phone = phone;
		_budget = budget;
	}
	// Gets or sets name
	string getName() {
		return _name;
	}
	void setName(const string &name) {
		_name = name;
	}
	// Gets or sets phone
	string getPhone() {
		return _phone;
	}
	void setPhone(const string &phone) {
		_phone = phone;
	}
	// Gets or sets budget
	double getBudget() {
		return _budget;
	}
	void setBudget(double budget) {
		_budget = budget;
	}
};
 
 
// The 'Originator' class
class SalesProspect {
private:
	string _name;
	string _phone;
	double _budget;
public:
	// Gets or sets name
	string getName() {
		return _name;
	}
	void setName(const string &name) {
		_name = name;
		cout << "Name: " << _name << endl;
	}
	// Gets or sets phone
	string getPhone() {
		return _phone;
	}
	void setPhone(const string &phone) {
		_phone = phone;
		cout << "Phone: " << _phone << endl;
	}
	// Gets or sets budget
	double getBudget() {
		return _budget;
	}
	void setBudget(double budget) {
		_budget = budget;
		cout << "Budget: " << _budget << endl;
	}
	// Stores memento
	Memento *SaveMemento() {
		cout << endl;
		cout << "Saving state --" << endl;
		return new Memento(_name, _phone, _budget);
	}
	// Restores memento
	void RestoreMemento(Memento *memento) {
		cout << endl;
		cout << "Restoreing state --" << endl;
		setName(memento->getName());
		setPhone(memento->getPhone());
		setBudget(memento->getBudget());
	}
};
 
 
// The 'Caretaker' class
class ProspectMemory {
private:
	Memento *_memento;
public:
	ProspectMemory() {
		_memento = NULL;
	}
	~ProspectMemory() {
		if (_memento) {
			delete _memento;
		}
	}
	// Property
	Memento* getMemento() {
		return _memento;
	}
	void setMemento(Memento *memento) {
		_memento = memento;
	}
};
 
 
// Entry point into console application.
int main() {
	SalesProspect *s = new SalesProspect;	// prospect: 見込み
	s->setName("Noel van Halen");
	s->setPhone("(412) 256-0990");
	s->setBudget(25000.0);	// budget: 予算
 
	// Store internal state
	ProspectMemory *m = new ProspectMemory;
	m->setMemento(s->SaveMemento());
 
	// Continue changing originator
	s->setName("Leo Welch");
	s->setPhone("(310) 209-7111");
	s->setBudget(1000000.0);
 
	// Restore saved state
	s->RestoreMemento(m->getMemento());
 
	delete s;
	delete m;
	// Wait for user
	return 0;
}
 


参考サイト

デザインパターンを“喩え話”で分かり易く理解する
http://www.netlaputa.ne.jp/~hijk/study/oo/designpattern.html



デザインパターンの骸骨たち
http://www002.upp.so-net.ne.jp/ys_oota/mdp/
最終更新:2011年12月14日 01:16