简体   繁体   English

在c宏中使用if else

[英]Using if else in c macros

i'm trying to define the following macro: 我正在尝试定义以下宏:

#define UTF8_2B(c) if((0xc0 & c) == 0xc0){return 1;}

But i'm met with the error: 但我遇到了错误:

expected expression before ‘if’

The macro is called like so: 像这样调用宏:

int i = UTF8_2B(c);

Where c is an unsigned char read from a file. 其中c是从文件中读取的unsigned char。

Why does this happen? 为什么会这样? Can you not use if else statements in macros? 你能否在宏中使用if else语句? Also, I've read that it's not a good idea to use semicolon in your macros, but i didn't understand why. 另外,我已经读过在你的宏中使用分号不是一个好主意,但我不明白为什么。 I'm new to c so the more thorough the answer the better. 我是c的新手,所以答案越彻底越好。

C (and C++) preprocessor macros are essentially "copy-paste" with argument substitution. C(和C ++)预处理器宏基本上是“复制 - 粘贴”,带有参数替换。 So your code becomes: 所以你的代码变成:

int i = if((0xc0 & c) == 0xc0){return 1;}

And this is invalid syntax. 这是无效的语法。

You're assigning the result of your macro to a variable. 您将宏的结果分配给变量。 You cannot do that with the current macro ( return returns from the current function, and doesn't return something to be assigned to i : so not what you want). 你不能用当前的宏做这个(从当前函数return返回,并且不返回要分配给i东西:所以不是你想要的)。

If you're using gcc , you can view what your pre-processed code looks like with the -E command line. 如果您正在使用gcc ,则可以使用-E命令行查看预处理代码的外观。

So you can use if in macros, but not in macros that are used like functions, which are supposed to return a value. 所以你可以在宏中使用if ,但不能在像函数一样使用的宏中使用if ,它们应该返回一个值。

Moreover: 此外:

  • if c is a complex expression, operator precedence could make the macro generate wrong code 如果c是一个复杂的表达式,运算符优先级可能会使宏生成错误的代码
  • the macro should provide a way to require semicolon, so IDEs and human readers see that as a normal function 宏应该提供一种需要分号的方法,因此IDE和人类读者将其视为正常函数

I'd propose a simple test instead (which yields 1 if true, 0 otherwise), which meets the "need semicolon" standard and is safe to use with a complex c expression: 我建议改为一个简单的测试(如果是真的则产生1,否则产生0),这符合“需要分号”标准并且可以安全地与复杂的c表达式一起使用:

#define UTF8_2B(c) ((0xc0 & (c)) == 0xc0)

The ternary operator exists for this purpose. 为此目的存在三元运算符。 Assuming you want 1 if true and 0 if false, the correct macro is: 假设你想要1如果为真而0则为假,正确的宏是:

 #define UTF8_2B(c) (((c) & 0xC0) == 0xC0 ? 1 : 0)

Now you can assign the result. 现在您可以分配结果。 Using return in a macro will return from the enclosing function, not from the macro, and is almost always a bad idea. 在宏中使用return将从封闭函数返回,而不是从宏返回,并且几乎总是一个坏主意。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM