在C语言中,常常看到这样的宏:
1. 我们可以这样:
#define BAR(x) foo(x); goo(x)
验证一下啊:
if (condition)
BAR(1);
else
;
编译器将宏展开为:
if (condition)
foo(1); goo(1);
else
;
幸好这里编译器都不会让你过去(error: ‘else’ without a previous ‘if’), 不然goo(1)将会不辞辛劳的一直运行了。
2. 好的,那我们加上{}不就好使了。真的吗?
#define BAR(x) {foo(x); goo(x);}
验证一下啊:
if (condition)
BAR(1);
else
;
编译器将宏展开为:
if (condition)
{foo(1); goo(1);};
else
;
编译器依然会给出,error: ‘else’ without a previous ‘if’的错误信息。
现在就只能:
if (condition)
BAR(1)
else
;
如此怪异,语句后没有了";".
注意:为什么常常在编码规范中要求,即使if下只有一条语句,也加上大括号。
如果写成
if (condition){
BAR(1);
}
else
;
这样,如果有新手程序员写了如#define BAR(x) foo(x);goo(x)的句子,也不会有问题了。
3. 常规写法:
最后,预编译是危险的,建议直接将BAR定义为函数。
#define FOO(X) do { f(X); g(X); } while (0)
#define FOO(X) if (1) { f(X); g(X); } else
while(0)? if(1)? 拜托,这样毫无意义的判断!但为什么会被大量使用呢?
1. 我们可以这样:
#define BAR(x) foo(x); goo(x)
验证一下啊:
if (condition)
BAR(1);
else
;
编译器将宏展开为:
if (condition)
foo(1); goo(1);
else
;
幸好这里编译器都不会让你过去(error: ‘else’ without a previous ‘if’), 不然goo(1)将会不辞辛劳的一直运行了。
2. 好的,那我们加上{}不就好使了。真的吗?
#define BAR(x) {foo(x); goo(x);}
验证一下啊:
if (condition)
BAR(1);
else
;
编译器将宏展开为:
if (condition)
{foo(1); goo(1);};
else
;
编译器依然会给出,error: ‘else’ without a previous ‘if’的错误信息。
现在就只能:
if (condition)
BAR(1)
else
;
如此怪异,语句后没有了";".
注意:为什么常常在编码规范中要求,即使if下只有一条语句,也加上大括号。
如果写成
if (condition){
BAR(1);
}
else
;
这样,如果有新手程序员写了如#define BAR(x) foo(x);goo(x)的句子,也不会有问题了。
3. 常规写法:
#define BAR(x) do { \
int ret = foo(x);\
if (ret == 0) goo(x);\
}while(0)
#define if(1){foo(x); goo(x);} else
最后,预编译是危险的,建议直接将BAR定义为函数。