備忘錄模式

模式定義:

在不破環(huán)封裝行性的前提下段直,捕獲一個(gè)對(duì)象的內(nèi)部狀態(tài),并在該對(duì)象之外保存這個(gè)狀態(tài)溶诞。這樣就可以將該對(duì)象恢復(fù)到原先保存的狀態(tài)鸯檬。

模式場(chǎng)景

  1. 錄入大批人員資料的時(shí)候。正在錄入當(dāng)前人資料時(shí)螺垢,發(fā)現(xiàn)上一個(gè)人錄錯(cuò)了喧务,此時(shí)需要恢復(fù)到上一個(gè)人的資料,進(jìn)行修改枉圃。
  1. Word編輯時(shí)功茴,忽然斷電或電腦死機(jī),再打開時(shí)孽亲,可以看到Word提示你恢復(fù)到以前的文檔坎穿。

模式結(jié)構(gòu)

模式結(jié)構(gòu)
  1. Memento:備忘錄。主要用來(lái)存儲(chǔ)原發(fā)器對(duì)象的內(nèi)部狀態(tài)墨林,但是具體需要存儲(chǔ)哪些數(shù)據(jù)是由原發(fā)器對(duì)象來(lái)決定的赁酝。另外備忘錄應(yīng)該只能由原發(fā)器對(duì)象來(lái)訪問(wèn)它內(nèi)部的數(shù)據(jù),原發(fā)器外部的對(duì)象不應(yīng)該能訪問(wèn)到備忘錄對(duì)象的內(nèi)部數(shù)據(jù)旭等。

  2. Originator:原發(fā)器酌呆。使用備忘錄來(lái)保存某個(gè)時(shí)刻原發(fā)器自身的狀態(tài),也可以使用備忘錄來(lái)恢復(fù)內(nèi)部狀態(tài)搔耕。

  1. Caretaker:備忘錄管理者隙袁,或者稱為備忘錄負(fù)責(zé)人。主要負(fù)責(zé)保存?zhèn)渫泴?duì)象弃榨,但是不能對(duì)備忘錄對(duì)象的內(nèi)容進(jìn)行操作或檢查菩收。

代碼實(shí)現(xiàn)

UML圖

源碼

public interface FlowAMockMemento {
}

public class FlowAMock {
    private String flowName;
    private int tempResult;
    private String tempState;

    public FlowAMock(String flowName) {
        this.flowName = flowName;
    }

    public void runPhaseOne(){
        tempResult = 3;
        tempState = "phaseOne";
    }
    public void schema1(){
        this.tempState += ",Schema1";
        System.out.println(this.tempState+":now run " + tempResult);
        this.tempResult += 11;
    }

    public void schema2(){
        this.tempState += ",Schema2";
        System.out.println(this.tempState+":now run " + tempResult);
        this.tempResult += 22;
    }

    public FlowAMockMemento createMemento(){
        return new MementoImpl(this.tempResult,this.tempState);
    }

    public void setMemento(FlowAMockMemento memento){
        MementoImpl mementoImpl = (MementoImpl) memento;
        this.tempResult = mementoImpl.getTempResult();
        this.tempState = mementoImpl.getTempState();
    }

    /**
     * 真正的備忘錄對(duì)象,實(shí)現(xiàn)備忘錄窄接口
     * 實(shí)現(xiàn)成為私有內(nèi)部類
     */
    private static class MementoImpl implements FlowAMockMemento{
        @Getter
        private int tempResult;
        @Getter
        private String tempState;

        public MementoImpl(int tempResult, String tempState) {
            this.tempResult = tempResult;
            this.tempState = tempState;
        }
    }
}

@Data
public class FlowAMementoCareTaker{

    private FlowAMockMemento memento;
}

public class Client {
    public static void main(String[] args) {
        FlowAMock mock = new FlowAMock("testFlow");
        mock.runPhaseOne();

        FlowAMementoCareTaker careTaker = new FlowAMementoCareTaker();
        FlowAMockMemento memento = mock.createMemento();
        careTaker.setMemento(memento);

        mock.schema1();
        mock.setMemento(memento);
        mock.schema2();
    }
}

模式的優(yōu)缺點(diǎn)

模式的優(yōu)點(diǎn)

  1. 更好的封裝性

    備忘錄模式通過(guò)使用備忘錄對(duì)象,來(lái)封裝原發(fā)器對(duì)象的內(nèi)部狀態(tài)鲸睛,雖然這個(gè)對(duì)象是保存在原發(fā)器對(duì)象的外部娜饵,但是由于備忘錄對(duì)象的窄接口并不提供任何方法,這樣有效的保證了對(duì)原發(fā)器對(duì)象內(nèi)部狀態(tài)的封裝官辈,不把原發(fā)器對(duì)象的內(nèi)部實(shí)現(xiàn)細(xì)節(jié)暴露給外部箱舞。

  2. 簡(jiǎn)化了原發(fā)器

    備忘錄模式中遍坟,備忘錄對(duì)象被保存到原發(fā)器對(duì)象之外,讓客戶來(lái)管理他們請(qǐng)求的狀態(tài)晴股,從而讓原發(fā)器對(duì)象得到簡(jiǎn)化愿伴。

  3. 窄接口和寬接口

模式的缺點(diǎn)

  1. 可能會(huì)導(dǎo)致高開銷

    備忘錄模式基本的功能,就是對(duì)備忘錄對(duì)象的存儲(chǔ)和恢復(fù)电湘,它的基本實(shí)現(xiàn)方式就是緩存?zhèn)渫泴?duì)象隔节。這樣一來(lái),如果需要緩存的數(shù)據(jù)量很大怎诫,或者是特別頻繁的創(chuàng)建備忘錄對(duì)象,開銷是很大的刽虹。

思考

模式本質(zhì):保存和恢復(fù)內(nèi)部狀態(tài)

開發(fā)中的應(yīng)用場(chǎng)景:

  1. 棋類游戲呢诬,悔棋

  2. 普通軟件尚镰,撤銷操作

  3. 數(shù)據(jù)庫(kù)軟件中的,事務(wù)管理的狗唉,回滾操作

  4. Photoshop軟件

相關(guān)模式

  1. 備忘錄模式和命令模式
    這兩個(gè)模式可以組合使用涡真。

命令模式實(shí)現(xiàn)中,在實(shí)現(xiàn)命令的撤銷和重做的時(shí)候哆料,可以使用備忘錄模式,在命令操作的時(shí)候記錄下操作前后的狀態(tài)杏节,然后在命令撤銷和重做的時(shí)候,直接使用相應(yīng)的備忘錄對(duì)象來(lái)恢復(fù)狀態(tài)就可以了奋渔。
在這種撤銷的執(zhí)行順序和重做執(zhí)行順序可控的情況下壮啊,備忘錄對(duì)象還可以采用增量式記錄的方式嫉鲸,可以減少緩存的數(shù)據(jù)量。

  1. 備忘錄模式和原型模式
    這兩個(gè)模式可以組合使用歹啼。

在原發(fā)器對(duì)象創(chuàng)建備忘錄對(duì)象的時(shí)候玄渗,如果原發(fā)器對(duì)象中全部或者大部分的狀態(tài)都需要保存减江,一個(gè)簡(jiǎn)潔的方式就是直接克隆一個(gè)原發(fā)器對(duì)象。也就是說(shuō)捻爷,這個(gè)時(shí)候備忘錄對(duì)象里面存放的是一個(gè)原發(fā)器對(duì)象的實(shí)例。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末也榄,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子甜紫,更是在濱河造成了極大的恐慌,老刑警劉巖囚霸,帶你破解...
    沈念sama閱讀 216,843評(píng)論 6 502
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異拓型,居然都是意外死亡额嘿,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,538評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門劣挫,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)册养,“玉大人,你說(shuō)我怎么就攤上這事压固∏蚶梗” “怎么了?”我有些...
    開封第一講書人閱讀 163,187評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵帐我,是天一觀的道長(zhǎng)坎炼。 經(jīng)常有香客問(wèn)我,道長(zhǎng)拦键,這世上最難降的妖魔是什么谣光? 我笑而不...
    開封第一講書人閱讀 58,264評(píng)論 1 292
  • 正文 為了忘掉前任,我火速辦了婚禮矿咕,結(jié)果婚禮上抢肛,老公的妹妹穿的比我還像新娘。我一直安慰自己碳柱,他們只是感情好捡絮,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,289評(píng)論 6 390
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著莲镣,像睡著了一般福稳。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上瑞侮,一...
    開封第一講書人閱讀 51,231評(píng)論 1 299
  • 那天的圆,我揣著相機(jī)與錄音鼓拧,去河邊找鬼。 笑死越妈,一個(gè)胖子當(dāng)著我的面吹牛季俩,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播梅掠,決...
    沈念sama閱讀 40,116評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼酌住,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了阎抒?” 一聲冷哼從身側(cè)響起酪我,我...
    開封第一講書人閱讀 38,945評(píng)論 0 275
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎且叁,沒(méi)想到半個(gè)月后都哭,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,367評(píng)論 1 313
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡汇陆,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,581評(píng)論 2 333
  • 正文 我和宋清朗相戀三年执庐,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了看尼。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片媳拴。...
    茶點(diǎn)故事閱讀 39,754評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情憋他,我是刑警寧澤,帶...
    沈念sama閱讀 35,458評(píng)論 5 344
  • 正文 年R本政府宣布髓削,位于F島的核電站竹挡,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏立膛。R本人自食惡果不足惜揪罕,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,068評(píng)論 3 327
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望宝泵。 院中可真熱鬧好啰,春花似錦、人聲如沸儿奶。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,692評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)闯捎。三九已至椰弊,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間瓤鼻,已是汗流浹背秉版。 一陣腳步聲響...
    開封第一講書人閱讀 32,842評(píng)論 1 269
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留娱仔,地道東北人沐飘。 一個(gè)月前我還...
    沈念sama閱讀 47,797評(píng)論 2 369
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親耐朴。 傳聞我的和親對(duì)象是個(gè)殘疾皇子借卧,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,654評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容