iOS 中的Category
2016-03-13 16:54
661 查看
在之前的一段工作中遇到一个需求,就是在项目中所有的头像上添加跳转到类似个人信息的页面(我们公司的项目是一个IM的企业社交),但是以前没做这方面的考虑,真是疏忽,整个项目大约有十几个分散的头像,添加此功能的时候一般是有几种解决办法:
1.一个一个加(你要是这样写了,估计明天cto就让你滚蛋了)
2.创建一个UIImageView的子类,将需要的userID和一些跳转方法写到子类中去,然后将项目中的类名改一下,再赋值就行了,项目中有Storyboard或者Xib的话最好也改了(根据OC的多态性,不改也没关系)不过这个也不是最好的方法
3.就是通过Category,Category是只能添加方法的,但是通过runtime的一些函数可以添加属性,从而保存实例UserId之类的信息,(在AFNetWorking和SDWebImage中就多次使用的这种方法)
这就要说到Associated Objects 的实现原理
Associated Objects相关的函数主要有三种:
在#import <objc/runtime.h>中可以找到
void objc_setAssociatedObject(id object, const void *key, id value, objc_AssociationPolicy policy) //
用于给对象添加关联对象,传入 nil 则可以移除已有的关联对象;
objc_getAssociatedObject(id object, const void *key) //
用于获取关联对象
objc_removeAssociatedObjects(id object) //
用于移除一个对象的所有关联对象。(将该对象恢复成“原始”状态,一般不用,因为会除掉一些你不想除去的或者影响到同事的一些东西,一般用上边的就行了)
先介绍一下上边的几个需要关注的参数吧:
void *key ----- 通常key用static char类型或者直接使用选择器(selector)。
objc_AssociationPolicy
policy ---------
typedef OBJC_ENUM(uintptr_t, objc_AssociationPolicy) {
OBJC_ASSOCIATION_ASSIGN = 0, /**< Specifies a weak reference to the associated object. */
OBJC_ASSOCIATION_RETAIN_NONATOMIC = 1, /**< Specifies a strong reference to the associated object.
* The association is not made atomically. */
OBJC_ASSOCIATION_COPY_NONATOMIC = 3, /**< Specifies that the associated object is copied.
* The association is not made atomically. */
OBJC_ASSOCIATION_RETAIN = 01401, /**< Specifies a strong reference to the associated object.
* The association is made atomically. */
OBJC_ASSOCIATION_COPY = 01403 /**< Specifies that the associated object is copied.
* The association is made atomically. */
};
这个枚举中别的通过字面就可以理解,关于第一个OBJC_ASSOCIATION_ASSIGN其相当于assign和unsafe_unretained并不想当于weak,因为weak为空时会自动置nil,所以使用weak的时候要注意。
具体的实现就很简单了:
-(void)setImageUrl:(NSString *)imageUrl
{
objc_setAssociatedObject(self, @selector(imageUrl), imageUrl, OBJC_ASSOCIATION_COPY_NONATOMIC);
}
- (NSString *)imageUrl{
return objc_getAssociatedObject(self, @selector(imageUrl));
}
参考:http://nshipster.com/associated-objects/
1.一个一个加(你要是这样写了,估计明天cto就让你滚蛋了)
2.创建一个UIImageView的子类,将需要的userID和一些跳转方法写到子类中去,然后将项目中的类名改一下,再赋值就行了,项目中有Storyboard或者Xib的话最好也改了(根据OC的多态性,不改也没关系)不过这个也不是最好的方法
3.就是通过Category,Category是只能添加方法的,但是通过runtime的一些函数可以添加属性,从而保存实例UserId之类的信息,(在AFNetWorking和SDWebImage中就多次使用的这种方法)
这就要说到Associated Objects 的实现原理
Associated Objects相关的函数主要有三种:
在#import <objc/runtime.h>中可以找到
void objc_setAssociatedObject(id object, const void *key, id value, objc_AssociationPolicy policy) //
用于给对象添加关联对象,传入 nil 则可以移除已有的关联对象;
objc_getAssociatedObject(id object, const void *key) //
用于获取关联对象
objc_removeAssociatedObjects(id object) //
用于移除一个对象的所有关联对象。(将该对象恢复成“原始”状态,一般不用,因为会除掉一些你不想除去的或者影响到同事的一些东西,一般用上边的就行了)
先介绍一下上边的几个需要关注的参数吧:
void *key ----- 通常key用static char类型或者直接使用选择器(selector)。
objc_AssociationPolicy
policy ---------
typedef OBJC_ENUM(uintptr_t, objc_AssociationPolicy) {
OBJC_ASSOCIATION_ASSIGN = 0, /**< Specifies a weak reference to the associated object. */
OBJC_ASSOCIATION_RETAIN_NONATOMIC = 1, /**< Specifies a strong reference to the associated object.
* The association is not made atomically. */
OBJC_ASSOCIATION_COPY_NONATOMIC = 3, /**< Specifies that the associated object is copied.
* The association is not made atomically. */
OBJC_ASSOCIATION_RETAIN = 01401, /**< Specifies a strong reference to the associated object.
* The association is made atomically. */
OBJC_ASSOCIATION_COPY = 01403 /**< Specifies that the associated object is copied.
* The association is made atomically. */
};
这个枚举中别的通过字面就可以理解,关于第一个OBJC_ASSOCIATION_ASSIGN其相当于assign和unsafe_unretained并不想当于weak,因为weak为空时会自动置nil,所以使用weak的时候要注意。
具体的实现就很简单了:
-(void)setImageUrl:(NSString *)imageUrl
{
objc_setAssociatedObject(self, @selector(imageUrl), imageUrl, OBJC_ASSOCIATION_COPY_NONATOMIC);
}
- (NSString *)imageUrl{
return objc_getAssociatedObject(self, @selector(imageUrl));
}
参考:http://nshipster.com/associated-objects/
相关文章推荐
- 峰回路转,Firefox 浏览器即将重返 iOS 平台
- 峰回路转,Firefox 浏览器即将重返 iOS 平台
- 不可修补的 iOS 漏洞可能导致 iPhone 4s 到 iPhone X 永久越狱
- iOS 12.4 系统遭黑客破解,漏洞危及数百万用户
- 每日安全资讯:NSO,一家专业入侵 iPhone 的神秘公司
- [转][源代码]Comex公布JailbreakMe 3.0源代码
- 讲解iOS开发中基本的定位功能实现
- iOS中定位当前位置坐标及转换为火星坐标的方法
- js判断客户端是iOS还是Android等移动终端的方法
- iOS应用中UISearchDisplayController搜索效果的用法
- IOS开发环境windows化攻略
- iOS应用中UITableView左滑自定义选项及批量删除的实现
- 浅析iOS应用开发中线程间的通信与线程安全问题
- 检测iOS设备是否越狱的方法
- .net平台推送ios消息的实现方法
- 探讨Android与iOS,我们将何去何从?
- Android、iOS和Windows Phone中的推送技术详解
- iOS推送的那些事
- IOS 改变键盘颜色代码