美文网首页iOS启蒙iOS学习开发iOS学习笔记
iOS 设计模式: Singleton – 单例模式

iOS 设计模式: Singleton – 单例模式

作者: 孟豊Mike | 来源:发表于2017-02-19 23:56 被阅读62次

单例 的意思就是确保在程序运行过程中只创建一个对象实例,而可以被多次使用。如我们常见的网络请求类、工具类、和其他管理类等。作为一个iOS开发者,我们经常和单例打交道,比如:[NSUserDefaults standerUserDefaults], [UIApplication sharedApplication],[UIScreen mainScreen], [NSFileManager defaultManager]返回的都是单例对象。
我们在开源项目、苹果示例代码能见到无数使用单例的例子。Xcode 甚至有默认的 "Dispatch Once" 代码片段,使我们可以非常简单地在代码中添加一个单例。

"Dispatch Once" 代码片段

一、单例的作用

  • 它可以保证某个类在程序运行过程中最多只有一个实例,节省内存开销。如果某个对象需要被多个其它对象使用,那可以考虑使用单例,因为这样该类只使用一份内存资源。

注意点!!!! 单例应该只用来保存全局的状态,并且不能和任何作用域绑定。如果这些状态的作用域比一个完整的应用程序的生命周期要短,那么这个状态就不应该使用单例来管理。因为单例从创建后到彻底关闭程序前都会一直存在,如果过多的创建单例无疑浪费系统资源和影响系统效率

二、单例的三要点

  • 单例模式的三个要点:

1. 该类有且只有一个实例;(类的构造方法是私有的我们只需要重写allocWithZone方法,让初始化操作只执行一次)

2. 该类必须能够自行创建这个实例;(类提供一个类方法产生对象)

3. 该类必须能够自行向整个系统提供这个实例。(类中有一个私有的自己对象我们可以在.m文件中定义一个属性即可)

三、单例的实现步骤

1. 为单例对象创建一个静态实例,可以写成全局的,也可以在类方法里面实现,并初始化为nil;
  2. 提供一个类方法,方便外界访问;
  3. 重写allocWithZone方法,用来保证其他人直接使用alloc和init试图获得一个新实力的时候不产生一个新实例;
  4. 重写-copyWithZone方法和-MutableCopyWithZone方法

一般创建对象的步骤分为申请内存(alloc)、初始化(init)这两个步骤,我们要确保对象的唯一性,所以要在第一步拦截它。当我们调用alloc方法时,oc内部会调用allocWithZone这个方法来申请内存,我们覆写这个方法,然后在这个方法中调用shareInstance方法返回单例对象,这样就可以达到我们的目的。拷贝对象也是同样的原理,覆写copyWithZone方法,然后在这个方法中调用shareInstance方法返回单例对象。

#import "Tools.h"

@implementation Tools
// 创建静态对象 防止外部访问
static Tools *_instance;
+(instancetype)allocWithZone:(struct _NSZone *)zone
{
    @synchronized (self) {
        // 为了防止多线程同时访问对象,造成多次分配内存空间,所以要加上线程锁
        if (_instance == nil) {
           _instance = [super allocWithZone:zone];
      }
      return _instance;
}
// 为了使实例易于外界访问 我们一般提供一个类方法
// 类方法命名规范 share类名|default类名|类名
+(instancetype)shareTools
{
    //return _instance;
    // 最好用self 用Tools他的子类调用时会出现错误
    return [[self alloc]init];
}
// 为了严谨,也要重写copyWithZone 和 mutableCopyWithZone
-(id)copyWithZone:(NSZone *)zone
{
    return _instance;
}
-(id)mutableCopyWithZone:(NSZone *)zone
{
    return _instance;
}

也可以使用Xcode 默认的dispatch_once代码片段用 GCD的方式创建:
@implementation Singleton
static id _instance;

+ (instancetype)allocWithZone:(struct _NSZone *)zone{
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        _instance = [super allocWithZone:zone];
    });
    return _instance;
}

+ (instancetype)sharedSingleton{
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        _instance = [[self alloc] init];
    });
    return _instance;
}

- (id)copyWithZone:(NSZone *)zone{
    return _instance;
}
@end

四、使用单例的注意事项

  • 单例给我们带来方便的同时也有一定的副作用,因为单例对象一旦创建,对象指针是保存在静态区的,单例对象在堆中分配的内存空间只有在程序终止后才会释放,过多的单例必定会增大我们消耗的内存
  • 不要做断开单例类对象与类中静态引用的危险操作。
  • 多线程使用单例使用共享资源时,注意线程安全问题。

相关文章

  • 单例模式 Singleton Pattern

    单例模式-菜鸟教程 iOS中的设计模式——单例(Singleton) iOS-单例模式写一次就够了 如何正确地写出...

  • JAVA设计模式 - 单例模式

    JAVA设计模式 - 单例模式 单例模式(Singleton Pattern)是 Java 中最简单的设计模式之一...

  • 单例模式

    3、单例模式(Singleton) 单例对象(Singleton)是一种常用的设计模式。在Java应用中,单例对象...

  • 设计模式——单例模式

    设计模式——单例模式 单例模式(Singleton Pattern)是 Java 中最简单的设计模式之一,这种类型...

  • iOS单例设计模式

    在iOS的开发中,单例设计模式(Singleton Pattern)是用得最多的设计模式之一了。在iOS的SDK中...

  • 设计模式-单例模式(Singleton)

    单例模式(Singleton) 单例对象(Singleton)是一种常用的设计模式。在Java应用中,单例对象能保...

  • 设计模式

    单例模式 单例模式(Singleton Pattern)是 Java 中最简单的设计模式之一。这种类型的设计模式...

  • 设计模式与软件原则 (二):单例设计模式

    单例设计模式(Singleton Design Pattern) 单例设计模式是一种创造(creational)设...

  • 设计模式--单例模式

    单例模式(singleton) 单例模式最初的定义出现于《设计模式》(Addison-Wesley,1994) 单...

  • 设计模式《一》单例模式

    单例模式 单例模式(Singleton Pattern)是 Java 中最简单的设计模式之一。这种类型的设计模式属...

网友评论

    本文标题:iOS 设计模式: Singleton – 单例模式

    本文链接:https://www.haomeiwen.com/subject/wwdqwttx.html