Objective-C的单例模式如何新建和测试?

本文详细介绍了Objective-C编程语言中单例模式的建立及实现方法,包括静态全局对象的使用、防止实例化、深浅拷贝和dealloc的处理等步骤,并提供了非ARC和ARC模式下的实现代码示例。



所谓单例模式是一种最简单的设计模式之一,就是程序中一个类只对应着一个实例,在很多编程语言中都有这种模式,比如objective-c编程语言、Java语言。对于objective-c来说,其单例模式是怎样的呢?如何表现呢?今天小编围绕这个问题,整理了一篇相关文章,分享给大家,一起来get新技能吧。

 

单例模式一般用全局静态对象来实现。下面我们通过建立一个生成单例的类SingletonClass,在实现文件中定义各种方法来实现我们的单例模式。

 

1、单例模式一般用全局静态对象来实现,所以我们在SingletonClass.m中定义一个静态全局变量是少不了的:

 

//定义静态全局变量

staticSingletonClass *single = nil;

//定义静态全局变量

staticSingletonClass *single = nil;

 

2、上面的静态变量是定义在实现文件中的,所以是私有的,要想获取该类的实例得有个getInstance方法来获取实例,在给静态变量分配内存空间之前,首先要判断是否已经分配过啦,确保单例,如果分配过了就不分配了。

 

//获取静态全局对象

+(id)getInstance

{

    //如果没有生成对象,则为静态全局变量分配内存

    if (single == nil) {

        single = [[SingletonClass alloc] init];

    }

    return single;

}

//获取静态全局对象

+(id)getInstance

{

    //如果没有生成对象,则为静态全局变量分配内存

    if (single == nil) {

        single = [[SingletonClass alloc]init];

    }

    return single;

}

 

3、为了防止用户通过alloc和new来实例化对象,因此我们要对类方法allcoWithZone进行重写

 

//防止通过alloc或者new来创建新的对象我们要重写allocWithZone

+(id)allocWithZone:(NSZone*)zone

{

    if (single == nil) {

        single = [[super allocWithZone:zone]init];

    }

    return single;

}

//防止通过alloc或者new来创建新的对象我们要重写allocWithZone

+(id)allocWithZone:(NSZone*)zone

{

    if (single == nil) {

        single =[[superallocWithZone:zone]init];

    }

    return single;

}

 

4、为了防止用户把单例进行深浅拷贝,我们需要重写copyWithZone方法和mutableCopyWithZone方法,在重写方法之前我们的单例类必须遵循协议NSCoping和NSMutableCoping协议

 

遵循协议代码如下:

 

@interfaceSingletonClass : NSObject

 

//单例中获取单例对象的方法

+(id)getInstance;

 

//单例测试方法

-(void)singletonFunction;

 

@end

@interfaceSingletonClass:NSObject

 

//单例中获取单例对象的方法

+(id)getInstance;

 

//单例测试方法

-(void)singletonFunction;

 

@end

重写copyWithZone方法

 

 

//为了防止通过copy来创建新的实例我们要重写copyWithZone;

-(id)copyWithZone:(NSZone*)zone

{

    return self;

}

//为了防止通过copy来创建新的实例我们要重写copyWithZone;

-(id)copyWithZone:(NSZone*)zone

{

    return self;

}

重写mutableCopyWithZone方法

 

 

-(id)mutableCopyWithZone:(NSZone*)zone

{

    return self;

}

-(id)mutableCopyWithZone:(NSZone*)zone

{

    return self;

}

 

5、防止用户把创建的单例dealloc,我们需要重写retainCount方法

 

//重写retainCount方法,防止被dealloc,返回最大值

-(NSUInteger)retainCount

{

    return NSUIntegerMax;

}

//重写retainCount方法,防止被dealloc,返回最大值

-(NSUInteger)retainCount

{

    return NSUIntegerMax;

}

 

6、重写release,autorelease, retain方法

 

//重写retain,引用计数不变

-(id) retain

{

    return self;

}

 

//重写release

-(oneway void)release

{

}

 

//重写autorelease

-(id)autorelease

{

    return self;

}

//重写retain,引用计数不变

-(id) retain

{

    return self;

}

 

//重写release

-(oneway void)release

{

}

 

//重写autorelease

-(id)autorelease

{

    return self;

}

 

至此我们的单例模式基本创建完毕,下面开始我们的测试吧;

 

在main函数中的代码如下:

 

//单例模式的测试

SingletonClass*single1 = [SingletonClass getInstance];

SingletonClass*single2 = [SingletonClass new];

SingletonClass*single3 = [[SingletonClass alloc] init];

SingletonClass*single4 = [single1 copy];

SingletonClass*single5 = [single1 mutableCopy];

SingletonClass*single6 = [single1 retain];

[single1release];

 

[single1singletonFunction];

NSLog(@"single_retainCount= %lu", single1.retainCount);

 

//输出地址

NSLog(@"getInstance     single1_P = %p", single1);

NSLog(@"new             single2_P = %p", single2);

NSLog(@"allo            single3_P = %p", single3);

NSLog(@"copy            single4_P = %p", single4);

NSLog(@"mutableCopy     single5_P = %p", single5);

NSLog(@"retain          single6_P = %p", single6);

//单例模式的测试

SingletonClass*single1 = [SingletonClass getInstance];

SingletonClass*single2 = [SingletonClass new];

SingletonClass*single3 = [[SingletonClass alloc]init];

SingletonClass*single4 = [single1copy];

SingletonClass*single5 = [single1mutableCopy];

SingletonClass*single6 = [single1retain];

[single1release];

 

[single1singletonFunction];

NSLog(@"single_retainCount= %lu", single1.retainCount);

 

//输出地址

NSLog(@"getInstance     single1_P = %p", single1);

NSLog(@"new             single2_P = %p", single2);

NSLog(@"allo            single3_P = %p", single3);

NSLog(@"copy            single4_P = %p", single4);

NSLog(@"mutableCopy     single5_P = %p", single5);

NSLog(@"retain          single6_P = %p", single6);

运行结果如下:

 

 

2014-08-0716:04:44.207 Memory[20664:303] singleton Ps: 我是单例模式中得测试方法!!

2014-08-0716:04:44.207 Memory[20664:303] single_retainCount = 18446744073709551615

2014-08-0716:04:44.207 Memory[20664:303] getInstance    single1_P = 0x100204690

2014-08-0716:04:44.208 Memory[20664:303] new            single2_P = 0x100204690

2014-08-0716:04:44.208 Memory[20664:303] alloC           single3_P = 0x100204690

2014-08-0716:04:44.208 Memory[20664:303] copy           single4_P = 0x100204690

2014-08-0716:04:44.209 Memory[20664:303] mutableCopy    single5_P = 0x100204690

2014-08-0716:04:44.209 Memory[20664:303] retain         single6_P = 0x100204690

2014-08-0716:04:44.207 Memory[20664:303]singleton Ps: 我是单例模式中得测试方法!!

2014-08-0716:04:44.207 Memory[20664:303]single_retainCount = 18446744073709551615

2014-08-0716:04:44.207 Memory[20664:303]getInstance    single1_P = 0x100204690

2014-08-0716:04:44.208 Memory[20664:303] new            single2_P = 0x100204690

2014-08-0716:04:44.208 Memory[20664:303]alloC           single3_P = 0x100204690

2014-08-0716:04:44.208 Memory[20664:303]copy           single4_P = 0x100204690

2014-08-0716:04:44.209 Memory[20664:303]mutableCopy    single5_P = 0x100204690

2014-08-0716:04:44.209 Memory[20664:303]retain         single6_P = 0x100204690

单例的地址是不变的。

 

上面是在非ARC模式下得单例模式,那么在ARC模式下我们应如何实现我们的单例模式呢,我们下面就会给出ARC下的单例模式,用下面的方法,因没有重写alloc,copy等方法,通过alloc还是可以给该对象分配一个新对象的,上面是线程不安全的,下面是线程安全的:

 

+(id)sharedSingleton {

     static MySingleton *sharedSingleton = nil;

     static dispatch_once_t onceToken;

     dispatch_once(&onceToken, ^{

         sharedSingleton = [[self alloc] init];

     });

     return sharedSingleton;

 }

 + (id)sharedSingleton {

    static MySingleton *sharedSingleton = nil;

    static dispatch_once_tonceToken;

    dispatch_once(&onceToken, ^{

        sharedSingleton = [[self alloc] init];

    });

    return sharedSingleton;

 }

 

以上就是objective-c编程语言中,单例模式的建立及实现方法,有兴趣的童鞋可以尝试自己实现一下。



相关文章:《Objective-C中NSMutableArray的创建及使用


需求响应动态冰蓄冷系统与需求响应策略的优化研究(Matlab代码实现)内容概要:本文围绕“需求响应动态冰蓄冷系统与需求响应策略的优化研究”展开,基于Matlab代码实现,重点探讨了冰蓄冷系统在电力需求响应背景下的动态建模与优化调度策略。研究结合实际电力负荷与电价信号,构建系统能耗模型,利用优化算法对冰蓄冷系统的运行策略进行求解,旨在降低用电成本、平衡电网负荷,并提升能源利用效率。文中还提及该研究为博士论文复现,涉及系统建模、优化算法应用与仿真验证等关键技术环节,配套提供了完整的Matlab代码资源。; 适合人群:具备一定电力系统、能源管理或优化算法基础,从事科研或工程应用的研究生、高校教师及企业研发人员,尤其适合开展需求响应、综合能源系统优化等相关课题研究的人员。; 使用场景及目标:①复现博士论文中的冰蓄冷系统需求响应优化模型;②学习Matlab在能源系统建模与优化中的具体实现方法;③掌握需求响应策略的设计思路与仿真验证流程,服务于科研项目、论文写作或实际工程方案设计。; 阅读建议:建议结合提供的Matlab代码逐模块分析,重点关注系统建模逻辑与优化算法的实现细节,按文档目录顺序系统学习,并尝试调整参数进行仿真对比,以深入理解不同需求响应策略的效果差异。
综合能源系统零碳优化调度研究(Matlab代码实现)内容概要:本文围绕“综合能源系统零碳优化调度研究”,提供了基于Matlab代码实现的完整解决方案,重点探讨了在高比例可再生能源接入背景下,如何通过优化调度实现零碳排放目标。文中涉及多种先进优化算法(如改进遗传算法、粒子群优化、ADMM等)在综合能源系统中的应用,涵盖风光场景生成、储能配置、需求响应、微电网协同调度等多个关键技术环节,并结合具体案例(如压缩空气储能、光热电站、P2G技术等)进行建模与仿真分析,展示了从问题建模、算法设计到结果验证的全流程实现过程。; 适合人群:具备一定电力系统、能源系统或优化理论基础,熟悉Matlab/Simulink编程,从事新能源、智能电网、综合能源系统等相关领域研究的研究生、科研人员及工程技术人员。; 使用场景及目标:①开展综合能源系统低碳/零碳调度的科研建模与算法开发;②复现高水平期刊(如SCI/EI)论文中的优化模型与仿真结果;③学习如何将智能优化算法(如遗传算法、灰狼优化、ADMM等)应用于实际能源系统调度问题;④掌握Matlab在能源系统仿真与优化中的典型应用方法。; 阅读建议:建议结合文中提供的Matlab代码与网盘资源,边学习理论模型边动手调试程序,重点关注不同优化算法在调度模型中的实现细节与参数设置,同时可扩展应用于自身研究课题中,提升科研效率与模型精度。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值