Skip to content

Memento (Хранитель)

Шаблон проектирования "Хранитель" (Memento) позволяет сохранять и восстанавливать состояние объекта без раскрытия его внутренней структуры. Этот паттерн полезен, когда необходимо реализовать функциональность отмены или сохранения состояния, например, в текстовых редакторах или играх.

Основные компоненты паттерна "Хранитель":

  1. Хранитель (Memento): объект, который хранит состояние другого объекта.
  2. Производитель (Originator): объект, состояние которого нужно сохранить. Он создает хранитель и восстанавливает свое состояние из него.
  3. Управляющий (Caretaker): объект, который отвечает за сохранение и восстановление хранителей. Он не знает о внутреннем состоянии объекта, только о хранителе.

Пример на Java

Рассмотрим пример, в котором у нас есть текстовый редактор, который может сохранять и восстанавливать состояние текста.

import java.util.ArrayList;
import java.util.List;

// Хранитель
class Memento {
    private String state;

    public Memento(String state) {
        this.state = state;
    }

    public String getState() {
        return state;
    }
}

// Производитель
class TextEditor {
    private String text;

    public void setText(String text) {
        this.text = text;
    }

    public String getText() {
        return text;
    }

    public Memento save() {
        return new Memento(text);
    }

    public void restore(Memento memento) {
        text = memento.getState();
    }
}

// Управляющий
class Caretaker {
    private List<Memento> mementoList = new ArrayList<>();

    public void addMemento(Memento memento) {
        mementoList.add(memento);
    }

    public Memento getMemento(int index) {
        return mementoList.get(index);
    }
}

// Пример использования
public class MementoPatternExample {
    public static void main(String[] args) {
        TextEditor editor = new TextEditor();
        Caretaker caretaker = new Caretaker();

        // Сохраняем состояние
        editor.setText("Первый вариант текста");
        caretaker.addMemento(editor.save());

        editor.setText("Второй вариант текста");
        caretaker.addMemento(editor.save());

        editor.setText("Третий вариант текста");

        // Восстанавливаем состояние
        editor.restore(caretaker.getMemento(1));
        System.out.println("Восстановленный текст: " + editor.getText()); // Восстановленный текст: Второй вариант текста
    }
}

Объяснение кода:

  1. Класс Memento представляет хранитель, который хранит состояние текста. Он имеет метод getState, который возвращает сохраненное состояние.
  2. Класс TextEditor является производителем, который управляет текстом. Он может сохранять свое состояние в объекте Memento и восстанавливать его из хранителя.
  3. Класс Caretaker управляет хранителями. Он хранит список хранителей и предоставляет методы для добавления и получения хранителей.
  4. В методе main мы создаем экземпляр TextEditor и Caretaker. Мы сохраняем несколько состояний текста и затем восстанавливаем одно из них.

Таким образом, паттерн "Хранитель" позволяет сохранять и восстанавливать состояние объекта, не раскрывая его внутреннюю структуру. Это делает код более гибким и позволяет реализовать функциональность отмены и восстановления состояния.