IOS 宏定义
2015-10-20 11:43
465 查看
看喵神的宏定义的黑魔法学到了很多,在这里总结下。
一、单个“#”的使用
单个“#”表示将后面紧接的参数变成 C 字符串,如 :
#define Name(pro) @#pro
- (void)testName {
NSLog(@"|%@|",Name(self.dataArray));
}
2015-10-20 11:34:45.691 Shadow[1878:71990] setUp
2015-10-20 11:34:45.692 Shadow[1878:71990] |self.dataArray|
2015-10-20 11:34:45.692 Shadow[1878:71990] tearDown
二、双“##”的使用
双“##”表示连接运算符,是将前后两个参数名连接起来组成新的参数名。
听起来有点不可思议,看个例子吧。
#define __CZ_AppendName(a,b) a##b
- (void)testAppendMacros {
int a =1 , b =2, ab =0
;
int oldab = ab;
__CZ_AppendName(a,b) =3;
NSLog(@"a = %d , b = %d , oldab = %d , ab = %d ",a,b,oldab,ab);
}
2015-10-20 11:48:05.109 Shadow[1952:78380] setUp
2015-10-20 11:48:05.109 Shadow[1952:78380] a = 1 , b = 2 , oldab = 0 , ab = 3
2015-10-20 11:48:05.109 Shadow[1952:78380] tearDown
三、宏定义换行 “\”
有时候宏定义太长,需要换行显示使得排版精美。
#define MASAttachKeys(...) \
NSDictionary *keyPairs = NSDictionaryOfVariableBindings(__VA_ARGS__); \
for (id key in keyPairs.allKeys) { \
id obj = keyPairs[key]; \
NSAssert([obj respondsToSelector:@selector(setMas_key:)], \
@"Cannot attach mas_key to %@", obj); \
[obj setMas_key:key]; \
}
四、可变参数宏 __VA_ARGS__
OC在定义使用可变参数宏是,用...例如:
#define __CZ_ParamterNames(...) (@"" # __VA_ARGS__)
- (void)testMestor {
float a ,b, view1,view2;
//获取所有的key
NSLog(@"Name = %@",__CZ_ParamterNames(a,b,view1,view2));
}
2015-10-20 11:50:27.576 Shadow[1974:80161] setUp
2015-10-20 11:50:27.576 Shadow[1974:80161] Name = a,b,view1,view2
2015-10-20 11:50:27.585 Shadow[1974:80161] tearDown
现在开始动手实践吧
学了这么多新知识,就要动手练习练习,手写约束的同行都是知道iOS的NSDictionaryOfVariableBindings(...)
宏定义挺神奇的,传入View,即可得到包含同名元素的字典。 不妨模仿下这个宏:
先来简单分析下:
1.最明显的是接受可变参数
2.要把这些变量名字符串化得到keys
3.需要寻找NSDictionary对应的接受可变参数宏的方法
解决:
1.先来解决第一步,先定义宏__CZ_DictionaryWithValue(...)
2.将参数字符串化 @#__VA_ARGS__
3.需要相关方法,
+ (instancetype)dictionaryWithObjects:(NSArray *)objects forKeys:(NSArray *)keys;
+ (instancetype)arrayWithObjects:(id)firstObj, ...NS_REQUIRES_NIL_TERMINATION;
接下来就是简单地将一个字符串转化成一个keys数组: componentsSeparatedByString
整理:
#define __CZ_DictionaryWithValue(...) ({ \
NSDictionary* dic = [NSDictionary dictionaryWithObjects: \
[NSArray arrayWithObjects:__VA_ARGS__,nil] \
forKeys: \
[@#__VA_ARGS__ componentsSeparatedByString:@","]];
\
dic; \
})
- (void)testMestor {
NSString* str =@"haha";
NSNumber* num =@1;
NSDictionary* dic =__CZ_DictionaryWithValue(str,num);
NSLog(@"dic = %@",dic);
}
2015-10-20 11:50:27.576 Shadow[1974:80161] setUp
2015-10-20 11:50:27.577 Shadow[1974:80161] dic = {
num = 1;
str = haha;
}
2015-10-20 11:50:27.585 Shadow[1974:80161] tearDown
一、单个“#”的使用
单个“#”表示将后面紧接的参数变成 C 字符串,如 :
#define Name(pro) @#pro
- (void)testName {
NSLog(@"|%@|",Name(self.dataArray));
}
2015-10-20 11:34:45.691 Shadow[1878:71990] setUp
2015-10-20 11:34:45.692 Shadow[1878:71990] |self.dataArray|
2015-10-20 11:34:45.692 Shadow[1878:71990] tearDown
二、双“##”的使用
双“##”表示连接运算符,是将前后两个参数名连接起来组成新的参数名。
听起来有点不可思议,看个例子吧。
#define __CZ_AppendName(a,b) a##b
- (void)testAppendMacros {
int a =1 , b =2, ab =0
;
int oldab = ab;
__CZ_AppendName(a,b) =3;
NSLog(@"a = %d , b = %d , oldab = %d , ab = %d ",a,b,oldab,ab);
}
2015-10-20 11:48:05.109 Shadow[1952:78380] setUp
2015-10-20 11:48:05.109 Shadow[1952:78380] a = 1 , b = 2 , oldab = 0 , ab = 3
2015-10-20 11:48:05.109 Shadow[1952:78380] tearDown
三、宏定义换行 “\”
有时候宏定义太长,需要换行显示使得排版精美。
#define MASAttachKeys(...) \
NSDictionary *keyPairs = NSDictionaryOfVariableBindings(__VA_ARGS__); \
for (id key in keyPairs.allKeys) { \
id obj = keyPairs[key]; \
NSAssert([obj respondsToSelector:@selector(setMas_key:)], \
@"Cannot attach mas_key to %@", obj); \
[obj setMas_key:key]; \
}
四、可变参数宏 __VA_ARGS__
OC在定义使用可变参数宏是,用...例如:
#define __CZ_ParamterNames(...) (@"" # __VA_ARGS__)
- (void)testMestor {
float a ,b, view1,view2;
//获取所有的key
NSLog(@"Name = %@",__CZ_ParamterNames(a,b,view1,view2));
}
2015-10-20 11:50:27.576 Shadow[1974:80161] setUp
2015-10-20 11:50:27.576 Shadow[1974:80161] Name = a,b,view1,view2
2015-10-20 11:50:27.585 Shadow[1974:80161] tearDown
现在开始动手实践吧
学了这么多新知识,就要动手练习练习,手写约束的同行都是知道iOS的NSDictionaryOfVariableBindings(...)
宏定义挺神奇的,传入View,即可得到包含同名元素的字典。 不妨模仿下这个宏:
先来简单分析下:
1.最明显的是接受可变参数
2.要把这些变量名字符串化得到keys
3.需要寻找NSDictionary对应的接受可变参数宏的方法
解决:
1.先来解决第一步,先定义宏__CZ_DictionaryWithValue(...)
2.将参数字符串化 @#__VA_ARGS__
3.需要相关方法,
+ (instancetype)dictionaryWithObjects:(NSArray *)objects forKeys:(NSArray *)keys;
+ (instancetype)arrayWithObjects:(id)firstObj, ...NS_REQUIRES_NIL_TERMINATION;
接下来就是简单地将一个字符串转化成一个keys数组: componentsSeparatedByString
整理:
#define __CZ_DictionaryWithValue(...) ({ \
NSDictionary* dic = [NSDictionary dictionaryWithObjects: \
[NSArray arrayWithObjects:__VA_ARGS__,nil] \
forKeys: \
[@#__VA_ARGS__ componentsSeparatedByString:@","]];
\
dic; \
})
- (void)testMestor {
NSString* str =@"haha";
NSNumber* num =@1;
NSDictionary* dic =__CZ_DictionaryWithValue(str,num);
NSLog(@"dic = %@",dic);
}
2015-10-20 11:50:27.576 Shadow[1974:80161] setUp
2015-10-20 11:50:27.577 Shadow[1974:80161] dic = {
num = 1;
str = haha;
}
2015-10-20 11:50:27.585 Shadow[1974:80161] tearDown
相关文章推荐
- 峰回路转,Firefox 浏览器即将重返 iOS 平台
- 峰回路转,Firefox 浏览器即将重返 iOS 平台
- 不可修补的 iOS 漏洞可能导致 iPhone 4s 到 iPhone X 永久越狱
- iOS 12.4 系统遭黑客破解,漏洞危及数百万用户
- 每日安全资讯:NSO,一家专业入侵 iPhone 的神秘公司
- [转][源代码]Comex公布JailbreakMe 3.0源代码
- C/C++ 宏详细解析
- 深入探讨:宏、内联函数与普通函数的区别
- C++十六进制宏的用法详解
- 讲解iOS开发中基本的定位功能实现
- js判断客户端是iOS还是Android等移动终端的方法
- IOS开发环境windows化攻略
- C++基础入门教程(二):数据、变量、宏等
- 枚举和宏的区别详细解析
- .net平台推送ios消息的实现方法
- 浅析c++ 宏 #val 在unicode下的使用
- 探讨Android与iOS,我们将何去何从?
- Android、iOS和Windows Phone中的推送技术详解
- 如何在C语言的宏中使用类型关键字