Obective-C之宏定义
优(dan)美(teng)的前奏
宏定义这个东东,估计大家在代码中应该天天用吧。
在我刚刚做的一个项目中,各种往代码里码“#define”这种预处理指令。
什么动画时长啊,cell高度啊,cell的个数啊,balabala,看得我这个心烦。
拿一个例子来讲:
A程序猿定义了一个UITableViewCell的高度为45。
#define HEIGHT_TABLEVIEWCELL 45;
B程序猿也定义了一个UITableViewCell的高度为50。
#define HEIGHT_TABLEVIEWCELL 50;
然后B在他写的.m文件中引用了A的文件,然后...然后...就没有然后了。
总结一句话就是,TMD,太乱了。
经过查找资料,发现确实有人提出过问题,并且提出了“少用#define”的建议。
(很明显没有多少人遵循这一建议,大家还在开心的#define)
提出这一观点的论据主要有以下两点:
(1) 就是像我刚才举的例子一样,如果B引用了A的文件,并且A、B两人的文件中的预定义指令的名字相同,那么就会产生冲突,结果就是A 中的预定义指令把B中的预定义指令代替了。
(2)没有类型定义,就像#define HEIGHT_TABLEVIEWCELL 45;这句代码中,我们只能从后边的45来推测是int类型或者float类型。但是具体 是哪一种,代码中并不能体现出来。
所以基于以上两点,我们应该尽量少的使用#define这种预定义指令。
那不使用#define,我们使啥捏?
这个问题问滴有水平!^^!
那就分为两种情况跟大家聊聊:
在一个“编译单元”中使用
在Objective-C的语境下,“编译单元”一词通常指每个类的实现文件(以.m为后缀名)。
也就是说,我们只在当前这一个.m文件中使用。
简单使用
这种情况我们就可以使用static和const来修饰变量,例如 static const NSString *kClassName = @"DemoClass";
- static 能够限制当前变量只能在此编译单元中使用。
- const 能够限制当前变量只要被定义之后就不能被修改。
参考以下代码:
// DemoViewController.h
#import <UIKit/UIKit.h>
@interface DemoViewController : UIViewController
@end // DemoViewController.m
#import "DemoViewController.h" static const NSString *kClassName = @"DemoViewController"; @implementation DemoViewController
@end
命名规则
根据苹果官方代码我们可以发现,定义“编译单元”内的常量都是以"k",作为前缀。
在多个“编译单元”中使用
简单使用
若要在多个“编译单元”中使用,此类常量需放在“全局符号表”(global symbol table)中,以便可以在定义该常量的编译单元之外使用。
步骤稍微复杂一下,但是比把大象装冰箱要简单一点:
- 在.h文件中,使用extern、const关键字对变量进行声明。
- 在.m文件中,对.h文件中声明的变量进行定义。
参考以下代码:
// DemoViewController.h
#import <Foundation/Foundation.h> extern NSString *const DemoViewControllerClassName; @interface DemoViewController : UIViewController
@end // DemoViewController.m
#import "DemoViewController.h" NSString *const DemoViewControllerClassName =
@"DemoViewController"; @implementation DemoViewController
@end
注意const关键字的位置。
命名规则
为避免名称冲突,最好是用与之相关的类名做前缀。
系统框架中一般都这样做。例如UIKit就按照这种方式来声明用作通知名称的全局常量。
其中有类似UIApplicationDidEnterBackgroundNotification与UIApplicationWillEnterForegroundNotification这样的常量名。
总之,经过这个项目蛋疼的经历,大家还是在项目中尽量少的使用预定义指令。
另外附上咱家的微信公众号的二维码,没事儿可以扫扫哈。
有啥事儿大家可以随时留言交流。

Obective-C之宏定义的更多相关文章
- c++宏定义命令
在程序开始以#开头的命令,他们是预编译命令.有三类预编译命令:宏定义命令.文件包含命令.条件编译命令:今天聊聊宏定义: 宏定义命令将一个标识符定义为一个字符串,源程序中的该标识符均以指定的字符串来代替 ...
- dll导入导出宏定义,出现“不允许 dllimport 函数 的定义”的问题分析
建立dll项目后,在头文件中,定义API宏 #ifndef API_S_H #define API_S_H ...... #ifndef DLL_S_20160424 #define API _dec ...
- iOS之常用宏定义
下面我为大家提供一些常用的宏定义! 将这些宏定义 加入到.pch使用 再也不用 用一次写一次这么长的程序了 //-------------------获取设备大小------------------- ...
- linux中offsetof与container_of宏定义
linux内核中offsetof与container_of的宏定义 #define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->M ...
- Linux Kernel代码艺术——系统调用宏定义
我们习惯在SI(Source Insight)中阅读Linux内核,SI会建立符号表数据库,能非常方便地跳转到变量.宏.函数等的定义处.但在处理系统调用的函数时,却会遇到一些麻烦:我们知道系统调用函数 ...
- 面试问题5:const 与 define 宏定义之间的区别
问题描述:const 与 define 宏定义之间的区别 (1) 编译器处理方式不同 define宏是在预处理阶段展开: const常量是编译运行阶段使用: (2) 类型和安全检查不同 ...
- 关于Xcode8.1 / iOS10+ 真机测试系统打印或者宏定义打印不显示问题
前言: 最近做项目时遇到了很多莫名其妙的问题,其中就有这个打印(NSLog).也不多废话了,我们先来回顾一下Xcode8发布以来,我们遇到的一些关于打印的问题,当然也有解决方法: 1.Xcode8打印 ...
- JDStatusBarNotification和一些宏定义
// // AddTopicViewController.m // vMeet2 // // Created by 张源海 on 16/6/30. // Copyright © 2016年 h ...
- #define宏定义形式的"函数"导致的bug
定义了一个宏定义形式的"函数": #define SUM8(YY)\ {\ int Y = YY>>2;\ ...\ } 然后使用的时候,传入了一个同名的变量Y: i ...
- 黑马程序员——C语言基础 枚举 宏定义 自定义 static exterm
Java培训.Android培训.iOS培训..Net培训.期待与您交流! (以下内容是对黑马苹果入学视频的个人知识点总结) (一)枚举 1)枚举类型的定义 枚举是C语言中的一种基本数据类型,并不是构 ...
随机推荐
- 1.2 XmlBeanFactory的实例化
源代码分析,是一件既痛苦又快乐的事情,看别人写的代码是通过的,但当你能够看明白的时候,相信快乐也会随之而来,为了减少痛苦,更快的带来快乐, 本文以spring框架的XmlBeanFactory为入手点 ...
- Ubuntu的挂起和休眠
Ubuntu的挂起和休眠 之前一直没关注过这方面的信息,因为以前只是在台式机上面用Ubuntu,笔记本一直都是Windows.随着Windows越来越傻冒,最近决定将常用系统转为Ubuntu,才注意到 ...
- uva 10034
计算所有点之间的权值 然后就是最小生成树 #include<cstring> #include<string> #include<cstdio> #includ ...
- 想让安卓 APP 如丝般顺滑?
随着安卓手机市场占有率的节节攀升,随便在大街上找几个人估计 80% 用的都是安卓手机吧!用安卓手机的人这么多,不知道大家是否曾经感觉到过 APP 卡顿.死机?是否遇到应用程序无响应.闪退?本文就为大家 ...
- 解析php中die(),exit(),return的区别
die()停止程序运行,输出内容exit是停止程序运行,不输出内容return是返回值die是遇到错误才停止exit是直接停止,并且不运行后续代码,exit()可以显示内容.return就是纯粹的返回 ...
- Git管理unity3d项目
如果小组中没有足够的专业版license,用不了unity3d自带的version control,可以使用git来对项目进行版本控制:只不过需要建一个.gitignore文件在git项目管理的根目录 ...
- 在windows下使用git需要反复输入用户名和密码的问题
节选自我还在写的git文档中的一部分,用md写的,博客园竟然还不支持markdown,完全没有格式啊,懒得弄了,不过解决方法是没有问题的 在win下使用git,如果没有任何设置,一定会反复输入用户名和 ...
- Hadoop初步认识
Hadoop的介绍: Hadoop是一个适用于大数据的并行存储和计算的平台,是 Apache的一个用java 语言实现开源软件框架,实现了在大量计算机组成的集群中对海量数据进行分布式计算.Hadoop ...
- Maven、gradle、Ant、Eclipse IDE
Maven.gradle.Ant.Eclipse IDE之间的关系 http://wenku.baidu.com/view/d33208810912a21615792910.html?from=sea ...
- poj2750Potted Flower (线段树)
http://poj.org/problem?id=2750 之前做过类似的题 把一段的左连续最大.最小 右连续最大及最小及中间的连续更新出 就可以算出这段最大的连续和 注意不能全部加上 加上一特判 ...