用如下方法定义单例

@interface

singleton_interface(ClassName);

@end

实现单例在

@implemention

singleton_implemention(ClassName);

@end

 #define singleton_interface(class) + (instancetype)shared##class;
#define singleton_implementation(class)\
static class *_instance;\
\
+ (id)allocWithZone:(struct _NSZone *)zone \
{\
static dispatch_once_t onceToken;\
dispatch_once(&onceToken, ^{\
_instance = [[super allocWithZone:NULL] init];\
});\
\
return _instance;\
}\
\
+ (instancetype)shared##class \
{\
if(_instance == nil){\
_instance = [[class alloc] init];\
}\
\
return _instance;\
}\
\
- (id)copyWithZone:(struct _NSZone *)zone\
{\
return [class shared##class];\
}
 

但是 有时编译会出现错误:

duplicate symbol __instance in:

......class1.o

......class2.o

ld: 1 duplicate symbol for architecture x86_64

clang: error: linker command failed with exit code 1 (use -v to see invocation)

解决方法:

点击项目:

TARGETS-->Build Setting-->Apple LLVM 7.0 Code Generation -->No Common Blocks -->No

原因:我的理解,相同的代码块被两个类同时应用,commond + B build 时,编译器有时会误认为生成两个 目标文件是完全相同的。故而,要设置允许编译器识别有相同的代码块。实验:新建一个类 Director.h & Director.m,在 Director.h里导入Singleton.h

 #import <UIKit/UIKit.h>
#import "Singleton.h"
@interface Director : UIViewController
singleton_interface(Director);
@end

在Director.m里:

 #import "Director.h"

 @implementation Director
singleton_implementation(Director);
@end

再随便在新建一个类ViewController,在 viewController.h里导入Director.h

ViewController.h:

 #import "Director.h"

 @interface ViewController : UIViewController

 @end

ViewController.m

 #import "ViewController.h"

 @interface ViewController ()

 @end

 @implementation ViewController

 - (void)viewDidLoad {
[super viewDidLoad]; Director *d1 = [[Director alloc]init];
Director *d2 = [Director sharedDirector];
Director *d3 = [d1 copy]; NSLog(@"d1:%p\n,d2:%p\n,d3:%p",d1,d2,d3);
}

打印结果:地址完全一样

补充:

void dispatch_once( dispatch_once_t *predicate, dispatch_block_t block);其中第一个参数predicate函数,

dispatch_once_t 是一个predicate谓词,他约束后面的代码快在整个APP 里只被执行一次。而且该函数是GCD提供的线程安全的函数。

iOS 用宏定义写一个单例(Singleton)的更多相关文章

  1. 用 Java 写一个单例类?

    饿汉式单例 public class Singleton { private Singleton(){} private static Singleton instance = new Singlet ...

  2. 一个单例(Singleton),并说明单例的目的和好处

    单例的目的:保证一个类只有单一的实例,也就是说你无法通过new来创建这个类的一个新实例. 单例的好处:当一个对象在程序内部只能有一个实例的时候,它可以保证我们不会重复创建,而是始终指向同一个对象. S ...

  3. java 写一个单例设计程序,打印出该对象的地址

    class Test{ public static void main(String[] args) { singleton s1=singleton.getinstance(); singleton ...

  4. IOS 宏定义一个单例

    有时候是不是因为频繁地创建一个单例对象而头疼,一种方式要写好多遍?当然你可以用OC语言进行封装.但下面将介绍一种由C语言进行的封装.只要实现下面的方法,以后建单例对象只要二句话. 1.新建一个.h文件 ...

  5. iOS 使用宏定义函数和代码块

    iOS使用宏定义函数和代码块 今天在开发过程中碰到一个问题:就是父类中要向外发送通知,然后子类中或者其他类中来接收它.当然一般是把它写到类方法中去,但是有个问题,就是如果调用的类不是它的子类,就不能直 ...

  6. iOS常用宏定义--实用

    在这里给大家分享一些常用的宏定义,喜欢的小伙伴可以直接在项目中使用(持续更新)!为了大家使用方便,请点击GitHub - 宏定义头文件下载 ! 1.获取屏幕宽度与高度 #define SCREEN_W ...

  7. C++实现一个单例模板类

    单例模式在项目开发中使用得比较多,一个单例的模板类显得很有必要,避免每次都要重复定义一个单例类型 //非多线程模式下的一个单例模板类的实现 // template_singleton.h #inclu ...

  8. java单链表的实现自己动手写一个单链表

    单链表:单链表是一种链式存取的数据结构,用一组地址任意的存储单元存放线性表中的数据元素.链表中的数据是以结点来表示的,每个结点的构成:元素(数据元素的映象) + 指针(指示后继元素存储位置),元素就是 ...

  9. spring中如何向一个单例bean中注入非单例bean

    看到这个题目相信很多小伙伴都是懵懵的,平时我们的做法大都是下面的操作 @Component public class People{ @Autowired private Man man; } 这里如 ...

随机推荐

  1. 【python】Python标准库defaultdict模块

    来源:http://www.ynpxrz.com/n1031711c2023.aspx Python标准库中collections对集合类型的数据结构进行了很多拓展操作,这些操作在我们使用集合的时候会 ...

  2. Codeforces 389B(十字模拟)

    Fox and Cross Time Limit: 1000MS   Memory Limit: 262144KB   64bit IO Format: %I64d & %I64u Submi ...

  3. CSS备忘

    垂直居中:           先height再ling-height,都设成一样高 span 垂直居中:vertical-align:50%设置外边距:           margin-top,m ...

  4. struts2 标签 --<<s:url >

    Struts2中的链接标签 <s:url>和<s:a> 普通链接 Web程序中最普通的应用是链接到其他页面,下面看Welcome.jsp. <%@ page conten ...

  5. error: insufficient permissions for device: verify udev rules

    error: insufficient permissions for device: verify udev rules.See [http://developer.android.com/tool ...

  6. nginx增加ssl服务方法

    1.将申请到的ssl加密证书文件拷贝到nginx的conf目录下 如:server.pem.server.key 2.vim nginx.conf 例子: server { listen 443 ss ...

  7. Java Hour 46 SLF4J

    SLF4J(Simple Logging Facade for Jave). 上个章节在配置启动项目后,会报一个奇怪的错误,一开始以为是Maven 依赖有冲突,其实是和slf4j 密切相关的. 本文原 ...

  8. hdu 4021 n数码

    好题,6666 转自:http://www.cnblogs.com/kuangbin/archive/2012/08/23/2652410.html 题意:给出一个board,上面有24个位置,其中2 ...

  9. Messenger信使

    * Messenger用于Activity和Service之间消息传递 需求:activity来绑定服务,绑定成功后,将数据发送给service,service收到消息后,再发送信息给activity ...

  10. 对于Spark1.3进行编译

    编译其实是按照官方文档进行的,比较简单,文档地址是:http://spark.apache.org/docs/latest/building-spark.html 编译命令最终是: 先要执行: exp ...