以前一直以为宏的定义挺简单的,没有写过长的宏函数,最常用的是MAX()的定义,今天写一个宏函数的时候,相对于MAX()来说,稍微有点长,然后踩了一个小坑。
一开始将宏函数定义的时候,为了书写方便,将一个函数写成了几行,但是没有用连接符号连接起来,类似于下面
1 #define CHECK(ret) ({ 2 int ret; 3 ... 4 })
GCC总是提示ret不在范围内。想了半天没有明白怎么回事。
然后我发现了一个问题。
我的VIM定义宏函数时,#define那一行是显示的蓝色,但是我的 int ret,以及下面的都是普通的白色,然后我查看了我以前的代码,发现我的宏定义VIM显示的都是蓝色。
我马上想到的是我的下面定义的 int ret往下都没有包括进宏里面,这个宏,定义的是 CHECK(ret) == ({ ; 下面空出来的都是在main函数以外,这个当然会报错了,然后我用了连接符号,代码如下
1 #define CHECK(ret) ({ 2 int ret; 3 })
OK!!!
VIM中代码全是蓝色了,这样就识别了整个宏了。
细细想一下,宏的定义是怎么结束的,宏的结尾是没有分号的,那么推断宏是通过回车来结束的,也就是整个一行都是宏,所以当宏很长时,就要用到连接符来连接了。
这样这个推断也由上面的错误证明了。
这个坑不大,但是它也从侧面说明了,写程序,是个细心的活儿。这种小问题,以后就不要再犯了吧!
还有一点,连接符后面是不能有空格的,GCC会出现警告:
warning: backslash and newline separated by space
来自IBM网站上的解释是:
Solution: The backslash (\) character is used as the continuation character to continue #define statements and strings to the next line. GCC expects the backslash character to be the very last character on the line. This warning indicates that there is a space after the backslash. Delete the space and any other characters that come after the backslash.