设计模式中的Memento备忘录模式的在iOS App开发中的运用

 更新时间:2016年03月23日 16:53:56   作者:TonyGo  
这篇文章主要介绍了设计模式中的Memento备忘录模式的在iOS App开发中的运用,Memento着重于捕获和具体化当前对象的内部状态,需要的朋友可以参考下

备忘录模式。顾名思义,备忘录模式的初衷就是为了返回上一个状态而设计的。从名字看起来一目了然,好吧,还是老样子,先给出定义。

备忘录(Memento):在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态。这样以后就可将该对象恢复到原先保存的状态。

定义看起来搞的很专业,其实就是保存上一个状态,以便日后恢复用。好比是在玩游戏,在打大Boss之前担心第一次打不过,先存个盘,万一玩儿完了,还可以恢复状态重新PK。

下面给出类结构图。

2016323164621128.jpg (500×290)

Originator(原发器):记录当前时刻的内部状态,负责定义哪些属于需要备份的状态,负责创建memento,负责从memento恢复状态。

Memento(备忘录):负责存储Originator的内部状态,在需要时提供给Originator内部状态。

Caretaker(看管人):将Memento保存在安全的地方,并负责提取。

一句话概括:Originator创建一个包含其状态的Memento交给Caretaker保管,Caretaker不知如何与Memento交互,只负责把Memento在安全的地方保存好。
从上面这张图来看,关系比较简单吧。那么备忘录模式一般都用在什么场合呢?

Memento模式比较适用于功能比较复杂的,但需要维护或记录属性历史的类,或者需要保存的属性只是众多属性中的一小部分时,Originator可以根据保存的Memento信息还原到前一状态。有时候一些对象的内部信息必须保存在对象以外的地方,但是必须要由对象自己读取,这时,使用备忘录可以把复杂的对象内部信息对其他的对象屏蔽起来。当然了,最大的作用还是在于当角色的状态改变的时候,有可能这个状态无效,这时候就可以使用暂时存储起来的备忘录将状态进行复原。好啦,其实翻来覆去就是为了恢复数据用的,车轱辘话就不多说了,下面给大家简单展示一下实现的代码吧。

Objective-C代码实现:

Originator:

复制代码 代码如下:

//发起人:记录当前时刻的内部状态,负责定义哪些属于备份范围的状态,负责创建和恢复备忘录数据。
 
#import <Foundation/Foundation.h>
@class NimoMemento;
 
@interface NimoOriginator : NSObject
 
@property (nonatomic, copy) NSString* state;
 
- (NimoMemento *)createMemento;
- (void)restoreMemento:(NimoMemento *)memento;
 
@end

复制代码 代码如下:

#import "NimoOriginator.h"
#import "NimoMemento.h"
 
@implementation NimoOriginator
 
- (NimoMemento *)createMemento
{
    NimoMemento *memento = [[NimoMemento alloc] initWithState:_state];
    return memento;
}
 
- (void)restoreMemento:(NimoMemento *)memento
{
    _state = memento.state;
}
 
- (NSString *)description
{
    return [NSString stringWithFormat:@"State:%@", _state];
}
 
@end

Memento:
复制代码 代码如下:

//备忘录:负责存储发起人对象的内部状态,在需要的时候提供发起人需要的内部状态。
 
#import <Foundation/Foundation.h>
 
@interface NimoMemento : NSObject
 
@property (nonatomic, copy, readonly) NSString *state;
- (id)initWithState:(NSString *)state;
 
@end

复制代码 代码如下:

#import "NimoMemento.h"
 
@interface NimoMemento()
 
@property (nonatomic, copy, readwrite) NSString *state;
 
 
@end

复制代码 代码如下:

@implementation NimoMemento
 
- (id)initWithState:(NSString *)state
{
    if (self = [super init]) {
        _state = [state copy];
    }
    
    return self;
}
 
@end


Caretaker:
复制代码 代码如下:

//管理角色:对备忘录进行管理,保存和提供备忘录。
 
#import <Foundation/Foundation.h>
@class NimoMemento;
 
@interface NimoCaretaker : NSObject
 
@property (nonatomic, assign) NimoMemento *memento;
 
@end

复制代码 代码如下:

//
//  NimoCaretaker.m
//  MementoDemo
//

#import "NimoCaretaker.h"
 
@implementation NimoCaretaker
 
@end


复制代码 代码如下:

Client:
 
#import <Foundation/Foundation.h>
#import "NimoOriginator.h"
#import "NimoMemento.h"
#import "NimoCaretaker.h"
 
int main(int argc, const char * argv[]) {
    @autoreleasepool {
        
        NimoOriginator *originator = [[NimoOriginator alloc] init];
        originator.state = @"Old";
        NSLog(@"%@", originator);
        NimoMemento *memento = originator.createMemento;
        
        NimoCaretaker *caretaker = [[NimoCaretaker alloc] init];
        caretaker.memento = memento;
        originator.state = @"New";
        NSLog(@"%@", originator);
        
        [originator restoreMemento:[caretaker memento]];
        NSLog(@"%@", originator);
    }
    return 0;
}

运行:

2015-08-12 20:27:39.184 MementoDemo[1160:34914] State:Old
2015-08-12 20:27:39.186 MementoDemo[1160:34914] State:New
2015-08-12 20:27:39.186 MementoDemo[1160:34914] State:Old

以上通用代码运行后虽然能得到期望的结果,但是并不完美,在Menmento类的实现中,我们把state属性以及initWithState初始化方法暴露在了公共接口中,这两者本应只提供给Originator与Menmento(即对Originator与Menmento提供宽接口,对Caretaker等其他对象提供窄接口)。在C++等其他面向对象语言中,一般使用private或friend进行声明。但在Objective-C中一切都是公有的,所以需要额外的技巧来实现。

通过类扩展将state属性以及initWithState初始化方法从主接口头文件NimoMemento.h中分离:

复制代码 代码如下:

//
//  NimoMemento+Private.h
//  MementoDemo
//
 
#import "NimoMemento.h"
 
@interface NimoMemento ()
 
@property (nonatomic, copy, readwrite) NSString *state;
- (id)initWithState:(NSString *)state;
 
@end

如此,只在Originator与Menmento中#import NimoMemento+Private.h,便实现了接口的私有化。

相关文章

  • Objective-C中NSLog输出格式大全

    Objective-C中NSLog输出格式大全

    这篇文章主要介绍了Objective-C中NSLog输出格式的相关资料,非常的简单,有需要的小伙伴可以参考下。
    2015-06-06
  • React Native搭建iOS开发环境

    React Native搭建iOS开发环境

    React Native的门槛不管是对于前端开发者还是移动端开发者来说都是很高的,既要懂原生又要懂js,技术栈是相当长的。但是没有关系,下面我们一步步来学习,慢慢成长吧!
    2016-09-09
  • iOS开发之XLForm的使用方法

    iOS开发之XLForm的使用方法

    这篇文章主要介绍了iOS开发之XLForm的使用方法,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2018-07-07
  • 理解Objective-C的变量以及面相对象的继承特性

    理解Objective-C的变量以及面相对象的继承特性

    这篇文章主要介绍了理解Objective-C的变量以及面相对象的继承特性,文中的所说的点语法即是'对象名.成员变量名'这种对变量的访问,需要的朋友可以参考下
    2016-01-01
  • iOS Block解开多年以来一直的误解

    iOS Block解开多年以来一直的误解

    这篇文章主要给大家介绍了关于iOS Block多年以来一直的误解如何解开的相关资料,文中通过图文介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2018-05-05
  • iOS实现百度外卖头像波浪的效果

    iOS实现百度外卖头像波浪的效果

    对于现在很多人来说,叫外卖就成了不可或缺的习惯。某日瞬间发现百度外卖的APP波浪效果很是吸引人,相比较其他的外卖APP,颜值略高些.(淘宝也有波浪的效果),遂就思考如何实现这种"浪"的效果,下面来一起看看。
    2016-08-08
  • IOS CocoaPods详细使用方法

    IOS CocoaPods详细使用方法

    自从有了CocoaPods以后,这些繁杂的工作就不再需要我们亲力亲为了,只需要我们做好少量的配置工作,CocoaPods会为我们做好一切
    2016-09-09
  • iOS实现微信朋友圈视频截取功能

    iOS实现微信朋友圈视频截取功能

    这篇文章主要介绍了iOS实现微信朋友圈视频截取功能,微信使用非常普遍,功能也很强大,不知道大家对微信朋友圈视频截取功能有没有了解,下面脚本之家小编给大家带来详解介绍,感兴趣的朋友一起看看吧
    2018-07-07
  • iOS项目开发--实现类似淘宝详情页面

    iOS项目开发--实现类似淘宝详情页面

    本篇文章主要介绍了iOS实现类似淘宝详情页面,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2016-11-11
  • iOS实现带指引线的饼状图效果(不会重叠)

    iOS实现带指引线的饼状图效果(不会重叠)

    饼状图对大家来说应该都不陌生,下面这篇文章主要给大家介绍了关于iOS实现带指引线的饼状图效果(不会重叠)的相关资料,文章通过示例代码介绍的非常详细,需要的朋友可以参考借鉴,下面随着小编来一起学习学习吧。
    2018-04-04

最新评论