C预处理器和操作顺序
C preprocessors and order of operations
我正在学习C语言,但是我不懂这个:
#define square(x) x*x
a = square(2+3) //a = 11
当这个运行时,为什么a
最终是11
?
展开为2+3*2+3
,相当于2+(3*2)+3
。使用括号来修复:
#define square(x) ((x)*(x))
现在用square(x++)
试试,你会遇到更多的问题(未定义的行为)。如果可以,请避免在宏中执行此操作。
square(2+3)
扩展为2+3*2+3
,相当于2+(3*2)+3
[*
优先级高于+
]
在gcc中,你可以使用-E
选项来查看你的预处理器生成了什么
C:UsersSUPER USER>type a.c
#define square(x) x*x
int main()
{
a = square(2+3); //a = 11
}
C:UsersSUPER USER>gcc -E a.c
# 1 "a.c"
# 1 "<built-in>"
# 1 "<command-line>"
# 1 "a.c"
int main()
{
a = 2+3*2+3;
}
补救试试这个
#define square(x) ((x)*(x))
尝试:
#define square(x) ((x)*(x))
由于2 + 3
在表达式x * x
中被逐字替换,因此它变成了2 + 3 * 2 + 3
,并且*
运算符具有更高的优先级,因此您无法获得预期的结果。
始终将宏参数和整个表达式括在括号中以避免这种情况:
#define SQUARE(x) ((x) * (x))
还要注意传递的任何表达式都将被求值两次,如果表达式具有诸如赋值或函数调用之类的副作用,则可能不希望这样做。在这些情况下,最好使用内联函数。
考虑一下在展开宏时会得到什么。c预处理器会将其展开为
a = 2 + 3 * 2 + 3
你需要正确定义你的宏。宏变量总是用圆括号括起来。这将给您预期的结果。
#define square(x) ((x)*(x))
宏展开是这样的:
a = ((2 + 3) * (2 + 3))
相关文章:
- 标记为 std::memory_order_seq_cst 的单个原子操作是否会在所有位置触发顺序一致性?
- C++和PEMDAS的优先顺序/操作?
- 内存排序或读取-修改-写入操作,仅(读/写)内存顺序
- 如果 RMW 操作没有任何变化,是否可以针对所有内存顺序对其进行优化
- MPI 归约操作中的求和顺序
- 操作顺序以最大限度地提高精度
- 在进行顺序计算时保持操作顺序
- 编译器是否会简化按顺序执行多次的操作
- 在C++中,当表达式涉及对象时,将表达式赋值到对象中时,是否有定义的操作顺序?
- C 操作顺序和模量
- C 的操作顺序用于初始化数组大小
- 访问类成员的C++操作顺序
- C++ 输入流:Solaris 与 Linux 中的操作顺序
- C++:循环增量部分的操作顺序
- 循环与操作顺序
- 这里的具体操作顺序是什么?
- if 表达式中的操作顺序是否更改
- 使用Spirit的语义操作顺序(参考Phoenix)
- 操作顺序不正确?(C++)
- C预处理器和操作顺序