Memento programtervezési minta
A Memento programtervezési minta biztosítja, hogy egy objektum visszaállítható legyen az előző állapotába.

A Memento minta három objektummal implementálható: originator (kezdeményező), caretaker (gondnok), memento (emlékeztető). Az originator egy objektum, aminek van valamilyen belső állapota. A caretaker valamit módosít az originator belső állapotán, azonban azt akarja, hogy lehetősége legyen visszavonni a változásokat. A caretaker először kér az originator-tól egy memento objektumot. Ezután valamilyen műveletet (vagy műveleteket) végez az originator-on, majd, ha vissza akarja állítani az előző állapotot, akkor visszaadja az originator-nak a memento objektumot. A memento objektum önmagában egy átlátszatlan objektum (a caretaker nem változtathatja meg, vagy nem ajánlott megváltoztatnia). Amikor ezt a mintát használjuk, ügyelni kell arra, hogy ez csak egy objektummal foglalkozik, az originator eközben megváltoztathat más objektumokat vagy erőforrásokat.

Különösen jól használható például visszavonás (undo/redo) funkcionalitás megvalósításakor dokumentumszerkesztés során. Előnye, hogy nem sérti az egységbezárás határait. Hátránya, hogy sokszor erőforrásigényes (pl. teljes dokumentumtartalom mentése, több példányban).

Java példa 
A következő Java program illusztrálja a Memento minta "visszavonás"ának használatát.

import java.util.List;
import java.util.ArrayList;
class Originator {
    private String state;
    // The class could also contain additional data that is not part of the
    // state saved in the memento..
 
    public void set(String state) {
        System.out.println("Originator: Setting state to " + state);
        this.state = state;
    }
 
    public Memento saveToMemento() {
        System.out.println("Originator: Saving to Memento.");
        return new Memento(this.state);
    }
 
    public void restoreFromMemento(Memento memento) {
        this.state = memento.getSavedState();
        System.out.println("Originator: State after restoring from Memento: " + state);
    }
 
    public class Memento {
        private final String state;
 
        public Memento(String stateToSave) {
            state = stateToSave;
        }
 
        public String getSavedState() {
            return state;
        }
    }
}
 
class Caretaker {
    public static void main(String[] args) {
        List<Originator.Memento> savedStates = new ArrayList<Originator.Memento>();
 
        Originator originator = new Originator();
        originator.set("State1");
        originator.set("State2");
        savedStates.add(originator.saveToMemento());
        originator.set("State3");
        // We can request multiple mementos, and choose which one to roll back to.
        savedStates.add(originator.saveToMemento());
        originator.set("State4");
 
        originator.restoreFromMemento(savedStates.get(1));   
    }
}

A program kimenete:
 Originator: Setting state to State1
 Originator: Setting state to State2
 Originator: Saving to Memento.
 Originator: Setting state to State3
 Originator: Saving to Memento.
 Originator: Setting state to State4
 Originator: State after restoring from Memento: State3

Ez a példa egy Stringet használ állapotként, amelyik egy megváltoztathatatlan objektum Java-ban.
Valós életbeli forgatókönyvek esetén az állapot csaknem minden esetben egy objektum lesz és ez esetben az állapot egy példányát kell használni.

Megjegyezzük, hogy megvalósítás rámutat egy hátrányra is: deklarálni kell egy belső osztályt. Jobb lenne, ha a mementó stratégiát egynél több objektumra lehetne alkalmazni.

Leginkább három módja van a mementó elérésének:
 Szerializáció.
 Egy osztályt deklarálunk ugyanabban a csomagban.
 Az objektum egy proxyn keresztül szintén elérhetővé tehető, az adott objektumon egy save/restore (mentés/visszatöltés) műveletén keresztül.

C# Példa 
A Memento minta lehetővé teszi, hogy rögzítsük egy objektum állapotát az egységbezárás megsértése nélkül, úgy, hogy később vissza tudjuk azt állítani. Itt egy olyan példa látható ahol a memento objektumot konkrétan arra használjuk, hogy visszavonjuk az objektumban történő változásokat:
//IVSR : Memento példa C# kód

    //eredeti objektum
    public class OriginalObject
    {
        public string String1 { get; set; }
        public string String2 { get; set; }
        public Memento MyMemento { get; set; }

        public OriginalObject(string str1, string str2)
        {
            this.String1 = str1;
            this.String2 = str2;
            this.MyMemento = new Memento(str1, str2);
        }
        public void Revert()
        {
            this.String1 = this.MyMemento.string1;
            this.String2 = this.MyMemento.string2;
        }
    }
    
    //memento objektum
    public class Memento
    {
        public readonly string string1;
        public readonly string string2;

        public Memento(string str1, string str2)
        {
            string1 = str1;
            string2 = str2;
        }
    }

Jegyzetek

Források

További információk

Kapcsolódó szócikkek 
Programtervezési minta, Viselkedési minta

Programtervezési minták
Java-kódpéldák
C Sharp-kódpéldák
A Memento programtervezési minta biztosítja , hogy egy objektum visszaállítható legyen az előző állapotába . A Memento minta három objektummal implementálható : originator ( kezdeményező ) , caretaker ( gondnok ) , memento ( emlékeztető ) . Az originator egy objektum , aminek van valamilyen belső állapota . A caretaker valamit módosít az originator belső állapotán , azonban azt akarja , hogy lehetősége legyen visszavonni a változásokat . A caretaker először kér az originator-tól egy memento objektumot . Ezután valamilyen műveletet ( vagy műveleteket ) végez az originator-on , majd , ha vissza akarja állítani az előző állapotot , akkor visszaadja az originator-nak a memento objektumot . A memento objektum önmagában egy átlátszatlan objektum ( a caretaker nem változtathatja meg , vagy nem ajánlott megváltoztatnia ) . Amikor ezt a mintát használjuk , ügyelni kell arra , hogy ez csak egy objektummal foglalkozik , az originator eközben megváltoztathat más objektumokat vagy erőforrásokat . Különösen jól használható például visszavonás ( undo/ redo ) funkcionalitás megvalósításakor dokumentumszerkesztés során . Előnye , hogy nem sérti az egységbezárás határait . Hátránya , hogy sokszor erőforrásigényes ( pl. teljes dokumentumtartalom mentése , több példányban ) . Java példa A következő Java program illusztrálja a Memento minta " visszavonás" ának használatát. import java.util.List ; import java.util.ArrayList ; class Originator { private String state ; / / The class could also contain additional data that is not part of the / / state saved in the memento . . public void set( String state ) { System.out.println ( " Originator : Setting state to " + state ) ; this.state = state ; } public Memento saveToMemento ( ) { System.out.println ( " Originator : Saving to Memento. " ) ; return new Memento( this.state ) ; } public void restoreFromMemento ( Memento memento ) { this.state = memento.getSavedState ( ) ; System.out.println ( " Originator : State after restoring from Memento : " + state ) ; } public class Memento { private final String state ; public Memento( String stateToSave ) { state = stateToSave ; } public String getSavedState ( ) { return state ; } } } class Caretaker { public static void main( String [ ] args ) { List<Originator.Memento> savedStates = new ArrayList<Originator.Memento> ( ) ; Originator originator = new Originator ( ) ; originator.set ( " State1 " ) ; originator.set ( " State2 " ) ; savedStates.add ( originator.saveToMemento ( ) ) ; originator.set ( " State3 " ) ; / / We can request multiple mementos , and choose which one to roll back to. savedStates.add ( originator.saveToMemento ( ) ) ; originator.set ( " State4 " ) ; originator.restoreFromMemento ( savedStates.get ( 1 ) ) ; } } A program kimenete : Originator : Setting state to State1 Originator : Setting state to State2 Originator : Saving to Memento . Originator : Setting state to State3 Originator : Saving to Memento . Originator : Setting state to State4 Originator : State after restoring from Memento : State3 Ez a példa egy Stringet használ állapotként , amelyik egy megváltoztathatatlan objektum Java-ban . Valós életbeli forgatókönyvek esetén az állapot csaknem minden esetben egy objektum lesz és ez esetben az állapot egy példányát kell használni . Megjegyezzük , hogy megvalósítás rámutat egy hátrányra is : deklarálni kell egy belső osztályt . Jobb lenne , ha a mementó stratégiát egynél több objektumra lehetne alkalmazni . Leginkább három módja van a mementó elérésének : Szerializáció . Egy osztályt deklarálunk ugyanabban a csomagban . Az objektum egy proxyn keresztül szintén elérhetővé tehető , az adott objektumon egy save/ restore ( mentés/ visszatöltés ) műveletén keresztül. C # Példa A Memento minta lehetővé teszi , hogy rögzítsük egy objektum állapotát az egységbezárás megsértése nélkül , úgy , hogy később vissza tudjuk azt állítani . Itt egy olyan példa látható ahol a memento objektumot konkrétan arra használjuk , hogy visszavonjuk az objektumban történő változásokat : //IVSR\ : Memento példa C # kód / /eredeti objektum public class OriginalObject { public string String1 { get ; set ; } public string String2 { get ; set ; } public Memento MyMemento { get ; set ; } public OriginalObject( string str1 , string str2 ) { this.String 1 = str1 ; this.String 2 = str2 ; this.MyMemento = new Memento( str1 , str2 ) ; } public void Revert ( ) { this.String 1 = this.MyMemento.string 1 ; this.String 2 = this.MyMemento.string 2; } } //memento objektum public class Memento { public readonly string string1 ; public readonly string string2 ; public Memento( string str1 , string str2 ) { string1 = str1 ; string2 = str2 ; } } Jegyzetek Források További információk Kapcsolódó szócikkek Programtervezési minta , Viselkedési minta Programtervezési minták Java-kódpéldák C Sharp-kódpéldák