当前位置: 首页 > news >正文

【iOS】MRC下的单例模式批量创建单例

单例模式的介绍和ARC下的单例请见这篇:【iOS】单例模式

目录

    • 关闭ARC环境
    • MRC下的单例
    • ARC下的单例
    • 批量创建单例
    • Demo


关闭ARC环境

首先关闭ARC环境,即打开MRC:

在这里插入图片描述
或是指定某特定目标文件为非ARC环境:

在这里插入图片描述
双击某个类文件,指定为ARC环境,输入-fobjc-arc,指定为MRC环境,输入-fno-objc-arc

MRC下的单例

MRC下,我们就需要手动释放资源,通过重写一些与资源创建与释放相关的方法,以保证单例对象的唯一。

SingletonByMRC.h

@interface SingletonByMRC : NSObject
+ (instancetype)sharedSingletonByMRC;
@end

SingletonByMRC.m

@implementation SingletonByMRCstatic SingletonByMRC* instanceVariable = nil;/*alloc方法内部会调用allocWithZone:参数zone时系统分配给App的内存*/
+ (instancetype)allocWithZone:(struct _NSZone *)zone {if (!instanceVariable) {static dispatch_once_t onceToken;dispatch_once(&onceToken, ^{  // 安全(这段代码只会被调用一次)instanceVariable = [super allocWithZone: zone];});}return instanceVariable;
}- (oneway void)release {//  allocWithZone中使用了GCD命令创建对象的代码只执行一次(单例),如果被释放则无法再创建//  重写release方法,替换为空操作,防止instanceVariable被释放
}//  重写retain方法
- (instancetype)retain {return self;
}//  重写retainCount锁定引用计数
- (NSUInteger)retainCount {return 1;
}//  重写init方法,防止单例所拥有的属性值被重置
//  让初始化的方法只能执行一次,自然属性值就没有机会被重置
- (instancetype)init {static dispatch_once_t onceToken;dispatch_once(&onceToken, ^{instanceVariable = [super init];});return instanceVariable;
}//  仿造系统的单例创建方式,提供类方法
+ (nonnull instancetype)sharedSingletonByMRC {// 由于我们已经重写了init方法保证了单例对象的唯一了,所以这里直接调用init方法即可。return [[self alloc] init];
}@end

ARC下的单例

与MRC的主要区别就是不用再手动去释放资源了。

SingletonByARC.m

#import "SingletonByARC.h"@implementation SingletonByARCstatic SingletonByARC* insVar = nil;+ (instancetype)allocWithZone:(struct _NSZone *)zone {if (!insVar) {static dispatch_once_t onceToken;dispatch_once(&onceToken, ^{insVar = [super allocWithZone: zone];});}return insVar;
}- (instancetype)init {static dispatch_once_t onceToken;dispatch_once(&onceToken, ^{insVar = [super init];});return insVar;
}+ (instancetype)sharedInstance {return [[self alloc] init];
}@end

批量创建单例

如果一个项目中需要多个单例,总不能把上面的代码一个一个复制粘贴再改改就完事了吧?那未免也太麻烦了。
我们可以利用快速且简单地创建单例。

首先先说下一些关于宏的知识:

  • 使用#define关键字来定义宏
  • 宏定义只能是单行的,不能换行

那现在来讨论下一些疑惑吧,你说宏只能单行,可是创建单例的代码可是有很多行呀!还有我们如何做到自定义类方法名(就是 sharedXXX )?我们来介绍下宏下的两个特殊符号:

符号作用
\用来转译换行符,即屏蔽换行符
##将两个相邻的标记(token)连接为一个单独的标记

简言之,就是\用于取消换行,##用于连接。

创建头文件Singleton.h存放头文件:

#define SingletonH(methodName) + (instancetype)shared##methodName;#define SingletonM(methodName) \
static id _instance = nil; \
+ (instancetype)allocWithZone:(struct _NSZone *)zone { \if (!_instance) { \static dispatch_once_t onceToken; \dispatch_once(&onceToken, ^{ \_instance = [super allocWithZone:zone]; \}); \} \return _instance; \
} \
\
- (instancetype)init { \static dispatch_once_t onceToken; \dispatch_once(&onceToken, ^{ \_instance = [super init]; \}); \return _instance; \
} \
\
+ (instancetype)shared##methodName { \return [[self alloc] init]; \
}

SingletonH(methodName)为声明宏,SingletonM(methodName)为实现宏。在每一行后面加上(反斜杠)取消换行,使用##来拼接传入的方法名,需要注意的是:最后一行不能加反斜杠。

SingletonClass.h文件中直接声明shareSingleMethod方法:

#import "Singleton.h"@interface SingletonClass : NSObject
SingletonH(SingleMethod);
@end

将方法名SingleMethod传入SingletonH();中就可以拼接为shareSingleMethod

SingletonClass.m直接实现创建单例类

#import "SingletonClass.h"@implementation SingletonClass
SingletonM(SingleMethod);
@end

运行结果:

请添加图片描述

最终我们仅仅用了“两”行代码(SingletonH();SingletonM();),成功创建出了一个单例类,这样是不是节省了大量多余冗杂的代码呢。

Demo

【Github】使用单例进行传值

在这里插入图片描述

相关文章:

【iOS】MRC下的单例模式批量创建单例

单例模式的介绍和ARC下的单例请见这篇:【iOS】单例模式 目录 关闭ARC环境MRC下的单例ARC下的单例批量创建单例Demo 关闭ARC环境 首先关闭ARC环境,即打开MRC: 或是指定某特定目标文件为非ARC环境: 双击某个类文件,指定…...

计算机网络期末复习

今天考专四,环境都蛮好的,试卷也很新,老师人也不错,明年再来。 又到期末考试咯,大家复习没有?还没复习啊?还不复???? 目录 第一章 1-02 试简述…...

python写一个获取竞品信息报告

要编写一个获取竞品信息报告的Python程序,首先需要明确您想要获取的竞品信息以及数据来源。在这个示例中,我将展示如何从网页提取竞品信息,并编写一个简单的报告。 假设您想要获取以下竞品信息: 1. 产品名称 2. 产品价格 3. 产品特…...

一文彻底理解机器学习 ROC-AUC 指标

在机器学习和数据科学的江湖中,评估模型的好坏是非常关键的一环。而 ROC(Receiver Operating Characteristic)曲线和 AUC(Area Under Curve)正是评估分类模型性能的重要工具。 这个知识点在面试中也很频繁的出现。尽管…...

【二】【动态规划NEW】91. 解码方法,62. 不同路径,63. 不同路径 II

91. 解码方法 一条包含字母 A-Z 的消息通过以下映射进行了 编码 : ‘A’ -> “1” ‘B’ -> “2” … ‘Z’ -> “26” 要 解码 已编码的消息,所有数字必须基于上述映射的方法,反向映射回字母(可能有多种方法&#xff…...

Python闯LeetCode--第3题:无重复字符的最长子串

Problem: 3. 无重复字符的最长子串 文章目录 思路解题方法复杂度Code 思路 一上来马上想到两层for循环暴力枚举,但是又立马想到复杂度是 O ( n 2 ) O(n^2) O(n2),思考了一下能否有更优解,于是想到用头尾两个指针来指定滑动窗口(主…...

HTML DOM 对象

HTML DOM 对象 1. 概述 HTML DOM(文档对象模型)是一个跨平台和语言独立的接口,它允许程序和脚本动态地访问和更新文档的内容、结构和样式。在HTML DOM中,文档被表示为节点树,其中每个节点代表文档中的一个部分,例如元素、文本或属性。HTML DOM对象是构成这个节点树的基…...

如何解决 BeautifulSoup 安装问题:从 BeautifulSoup 3 到 BeautifulSoup 4

在使用 Python 的过程中,解析 HTML 和 XML 数据是一项常见任务。BeautifulSoup 是一个非常流行的解析库。然而,最近在安装 BeautifulSoup 时,遇到了一些问题。本文将介绍如何解决这些问题,并成功安装 BeautifulSoup 4。 问题描述 …...

原型模式--深复制/浅复制

原型模式用于克隆复杂对象,由于new一个实例对象会消耗大部分时间,所以原型模式可以节约大量时间 1 public class Sheep implements Cloneable{2 private String name;3 private Date birth;4 public Sheep(String name, Date birth) {5 …...

C# TextBox模糊查询及输入提示

在程序中,我们经常会遇到文本框中不知道输入什么内容,这时我们可以在文本框中显示提示词提示用户;或者需要查询某个内容却记不清完整信息,通常可以通过文本框列出与输入词相匹配的信息,帮助用户快速索引信息。 文本框…...

Node入门以及express创建项目

前言 记录学习NodeJS 一、NodeJS是什么? Node.js 是一个开源和跨平台的 JavaScript 运行时环境 二、下载NodeJs 1.下载地址(一直点击next即可,记得修改安装地址) https://nodejs.p2hp.com/download/ 2.查看是否安装成功,打开命令行 nod…...

Cheat Engine CE v7.5 安装教程(专注于游戏的修改器)

前言 Cheat Engine是一款专注于游戏的修改器。它可以用来扫描游戏中的内存,并允许修改它们。它还附带了调试器、反汇编器、汇编器、变速器、作弊器生成、Direct3D操作工具、系统检查工具等。 一、下载地址 下载链接:http://dygod/source 点击搜索&…...

【实例分享】访问后端服务超时,银河麒麟服务器操作系统分析及处理建议

1.服务器环境以及配置 【机型】 处理器: Intel 32核 内存: 128G 整机类型/架构: x86_64虚拟机 【内核版本】 4.19.90-25.22.v2101.kylin.x86_64 【OS镜像版本】 kylin server V10 SP2 【第三方软件】 开阳k8s 2.问题现象描述 …...

Java中和的区别

在Java中,& 和 && 都是逻辑运算符,但它们之间存在一些重要的区别,特别是在它们如何评估其操作数以及它们的性能影响方面。 短路评估(Short-Circuit Evaluation): &&(逻辑…...

深入理解计算机系统 CSAPP 家庭作业6.34

第一步先求(S,E,B,m) 题目说共C32个字节,块大小B为16个字节,那就是分为两组:0,1.然后每组存4个int 每个4字节 CB*E*S .B16 ,直接映射的E就是1,所以S2 m为啥等于7? 通过写出两个数组所有的地址可以得出m7. 得出高速缓存的参数:(S,E,B,m)(2,1,16,7),注意图6-26每个参数的定义…...

[leetcode 141环形链表]双指针解决环形链表

Problem: 141. 环形链表 文章目录 思路Code 思路 首先想到如果链表为空直接返回false 其次想到用双指针,一个一回走一步,另一个一回走两步 如果是环形,总有一个时刻,两指针会指向同一个节点,而且该结点不能为空(空是快指针遍历完单链表了) Code /*** Definition for singly-li…...

【深度学习】Precision、Accuracy的区别,精确率与准确率:深度学习多分类问题中的性能评估详解

在深度学习的多分类问题中,Precision(精确率)和Accuracy(准确率)是两种常用的性能评估指标,它们各自有不同的定义和用途。 Precision(精确率)的中文发音是:pǔ rēi xī…...

DELL服务器插入新磁盘、创建虚拟磁盘、挂载磁盘步骤

文章目录 一、磁盘清理(可选,针对新硬盘是Foreign状态)1、进入VD Mgmt2、清理新硬盘配置 二、创建虚拟磁盘1、进入Device Settings2、创建虚拟磁盘 三、挂载磁盘到系统1、分区磁盘(注意实际磁盘的名称)2、格式化分区3、…...

springboot与flowable(10):网关服务(排他网关)

一、绘制流程图 排他网关用于对流程中的决策建模。当执行到这个网关时,会按照所有出口顺序流定义的顺序对它们进行计算。选择第一个条件为true的顺序流继续流程。例如员工请假时,小于等于3天由组长审批,大于3天由总监审批。流程案例&#xff…...

Web前端网页源代码:深入剖析与实用技巧

Web前端网页源代码:深入剖析与实用技巧 在Web开发的浩瀚领域中,前端网页源代码扮演着至关重要的角色。它不仅是网页的骨架,更是实现各种交互和视觉效果的基石。本文将从四个方面、五个方面、六个方面和七个方面,对Web前端网页源代…...

聊天页面样式

聊天页面样式 代码&#xff1a; <!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8" /><meta name"viewport" content"widthdevice-width, initial-scale1.0" /><link rel"styleshee…...

PHP入门教程3:数组和字符串操作

PHP入门教程3&#xff1a;数组和字符串操作 在前两篇文章中&#xff0c;我们学习了PHP的基础语法、控制结构和函数的使用。本文将重点介绍数组和字符串的高级操作&#xff0c;这些是PHP编程中非常常见且重要的内容。本文将包含以下几个部分&#xff1a; 数组的类型和操作多维…...

mariadb

MariaDB安装配置、使用、授权、增删改查以及数据库备份与恢复 MariaDB安装配置、使用、授权、增删改查以及数据库备份与恢复_mariadb安装及配置教程-CSDN博客mariadb 恢复&#xff1a; ERROR! MySQL server PID file could not be found! 170104 23:04:21 InnoDB: The InnoD…...

C/C++:指针用法详解

C/C&#xff1a;指针 指针概念 指针变量也是一个变量 指针存放的内容是一个地址&#xff0c;该地址指向一块内存空间 指针是一种数据类型 指针变量定义 内存最小单位&#xff1a;BYTE字节&#xff08;比特&#xff09; 对于内存&#xff0c;每个BYTE都有一个唯一不同的编号…...

JDK8-17新特性

一、JDK8新特性:Lambda表达式 1.Lambda表达式及其使用举例 Lambda是一个匿名函数&#xff0c;我们可以把Lambda表达式理解为是一段可以传递的代码(将代码像数据一样进行传递)。使用它可以写出更简洁、更灵活的代码。作为一种更紧凑的代码风格&#xff0c;使Java的语言表达能力…...

文件加载的管理:探索三种方法

目录 1. 空闲表法和空闲链表法 空闲表法 优点 缺点 示例 空闲链表法 优点 缺点 示例 优缺点对比 适用场景 综合示例 2. 位图法 概述 优点 缺点 适用场景 示例 位图法的操作 3. 成组链接法 概述 优点 缺点 适用场景 示例 实现细节 结语 在计算机系统中…...

【机器学习】基于Transformer架构的移动设备图像分类模型MobileViT

1.引言 1.1. MobileViT是什么&#xff1f; MobileViT是一种基于Transformer的轻量级视觉模型&#xff0c;专为移动端设备上的图像分类任务而设计。 背景与目的&#xff1a; MobileViT由Google在2021年提出&#xff0c;旨在解决移动设备上的实时图像分类需求。与传统的卷积神…...

grub引导LinuxMint

注意事项&#xff1a;文件系统必须是FAT32 安装 sudo apt install gparted -y 分区管理软件 使用gparted分区和查看设备路径 sudo apt-get install grub-efi-amd64 #/dev/sdd1 是需要制作分区引导的设备路径 sudo mount /dev/sdd1 /mnt/123 #bios sudo grub-install --targe…...

Hadoop 2.0:主流开源云架构(四)

目录 五、Hadoop 2.0访问接口&#xff08;一&#xff09;访问接口综述&#xff08;二&#xff09;浏览器接口&#xff08;三&#xff09;命令行接口 六、Hadoop 2.0编程接口&#xff08;一&#xff09;HDFS编程&#xff08;二&#xff09;Yarn编程 五、Hadoop 2.0访问接口 &am…...

PythonSQL应用随笔4——PySpark创建SQL临时表

零、前言 Python中直接跑SQL&#xff0c;可以很好的解决数据导过来导过去的问题&#xff0c;本文方法主要针对大运算量时&#xff0c;如何更好地让Python和SQL打好配合。 工具&#xff1a;Zeppelin 语法&#xff1a;PySpark&#xff08;Apache Spark的Python API&#xff09;…...

做营销型网站一般要多少钱/企业营销策划书如何编写

24.1 场景问题24.1.1 发送提示消息考虑这样一个实际的业务功能&#xff1a;发送提示消息。基本上所有带业务流程处理的系统都会有这样的功能&#xff0c;比如某人有新的工作了&#xff0c;需要发送一条消息提示他。从业务上看&#xff0c;消息又分成普通消息、加急消息和特急…...

做目录网站注意/营销的目的有哪些

通常项目中src下的子目录都会有一个style文件夹&#xff0c;专门用来存放全局的样式文件。这个style文件夹下&#xff0c;一般有reset.css、var.scss、mixin.scss、class.scss、index.scss一般都会在index.scss文件中引入其他文件做统一管理&#xff0c;并在main.js中引入index…...

北京专业的网站建设/网站开发用什么软件

使用DOM节点操作1、周期性创建雪花setInterval()2、雪花出现的位置随机function rand(m,n){return Math.floor(Math.random() * (n-m1)) m}document.documentElement.clientWidth || document.body.clientWidth3、控制雪花向下飘&#xff08;移动的步径&#xff09;var step …...

做二手房的端口网站/下载百度网盘app

前言 在项目中频繁遇到数组、集合和泛型&#xff0c;在使用vue时&#xff0c;用到最多的是数组&#xff1b;在后台时使用最多的是泛型&#xff0c;有时还用到IList&#xff0c;下面来学习一下它们之间的关系。 正文 数组 概念 一组类型相同的有序数据&#xff0c;它是…...

网站的外链是怎么做的/桂平seo关键词优化

从计算机到手机&#xff0c;计算平台的发展不断将人类文明推向新的高峰&#xff0c;但随着移动互联网领域的开发潜力逐渐殆尽&#xff0c;越来越多的科技爱好者和开发者将目光投向了下一代计算平台——机器人。作为蕴含重大机会的领域&#xff0c;机器人产业发展却没有理想中迅…...

网站建设课程设计/seo推广绩效考核指标是什么

&#xfeff;&#xfeff; 1、Android-Universal-Image-Loader 可以高度配置的网络图片缓存库&#xff0c;非常灵活&#xff0c;用户量最多 缓存过期实现&#xff1a; File cacheDir StorageUtils.getCacheDirectory(context); // or any other folder MemoryCacheAware&l…...