FLY
Life is like riding a bicycle, to keep your balance, you must keep moving.

#define 是宏命令,预处理指令,在编译前,由预处理器做简单替代(如同文本编辑的替代命令,把程序中的所有遇到的词,全部替代),不作正确性检查,不管含义是否正确照样带入,只有在编译已被展开的源程序时才会发现可能的错误并报错。

#define 不是语句,不要在行末加分号,否则会连分号一块置换。

如何定义宏、取消宏 (句末不带分号)

  #define [Name] [Value] //定义宏

  #undef [Name] //取消宏

  #define PI (3.1415926) //普通宏

  #define max(a,b) ((a)>(b)? (a),(b)) //带参数的宏

1.简单的define定义

  #define DATA 1000  //一个简单的DATA定义,它代表1000

  if(i<DATA){.........}  //编译器在编译时,将DATA替换为1000。

  这样的定义看起来类似于普通的常量定义CONST,但也有着不同,因为define的定义更像是简单的文本替换,而不是作为一个量来使用,这个问题在下面反映的尤为突出。

2.define的“函数定义”

  define可以像函数那样接受一些参数,如下

  #define max(x,y) (x)>(y)?(x):(y) //若句末带分号,后面执行count<<"max:"<<(max(a,b))<<endl;会报错误。

  因为这个“函数”没有类型检查,就好像一个函数模板似的,当然,它绝对没有模板那么安全就是了。可以作为一个简单的模板来使用而已。

  但是这样做的话存在隐患,例子如下:

  (1)#define Add(a,b) a+b

          遇到c * Add(a,b) * d时,对Add(a,b)进行简单替换,式子为:c*a + b*d  

  (2)#define pin (int*)

      pin a,b;  //替换后为int* a,b;

  本意是a和b都是int型指针,但实际为:a是int型指针,而b是int型变量。此时应该使用typedef来代替define,这样a和b就都是int型指针了。

  定义时养成一个良好的习惯,建议所有的层次都要加括号。

  define可以替代多行的代码,例如MFC中的宏定义:

#define MACRO(arg1, arg2) do { \ 
    /* declarations */ \ 
    stmt1; \ 
    stmt2; \ 
    /* ... */ \ 
} while(0) /* (no trailing ; ) */ 

  关键是要在每一个换行的时候加上一个"\" 
  摘抄自http://www.blog.edu.cn/user1/16293/archives/2005/115370.shtml 修补了几个bug

3.define条件编译

  #ifdef XXX…(#else) …#endif

  #ifndef XXX … (#else) … #endif

  例如

  #ifdef DV22_AUX_INPUT   

  #define AUX_MODE 3    

  #else   

  #define AUY_MODE 3   

  #endif

  在大规模的开发过程中,特别是跨平台和系统的软件里,define最重要的功能是条件编译。

1 #ifdef WINDOWS 
2 ...... 
3 ...... 
4 #endif 
5 #ifdef LINUX 
6 ...... 
7 ...... 
8 #endif 

  可以在编译的时候通过#define设置编译环境 。

  关键是十分容易产生错误,包括机器和人理解上的差异等等。

4.define避免重复包含

  重复包含(重复定义) 由于头文件包含可以嵌套,那么C文件就有可能包含多次同一个头文件,就可能出现重复定义的问题的。

  通过条件编译开关来避免重复包含(重复定义)

  例如

  #ifndef __headerfileXXX__

  #define __headerfileXXX__

  …

  文件内容

  …

  #endif

posted on 2012-12-19 16:29  juice_li  阅读(204)  评论(0编辑  收藏  举报