规范中哪里定义了这种避免宏扩展的方式?

问题描述 投票:0回答:1

给出以下代码:

#include <limits>
#include <Windows.h>
int main()
{
    std::numeric_limits<double>::max();
}

我可以使用额外的括号来避免 Windows.h 中

max()
的预处理器宏扩展:

#include <limits>
#include <Windows.h>
int main()
{
    (std::numeric_limits<double>::max)();
}

这个“功能”有名字吗?这个“特性”是在 C++ 规范的哪里定义的?我想了解更多。我搜索了“类函数宏”,但没有找到这种避免宏扩展的相关条目。

如果版本很重要,那么 C++14,但如果原理没有改变,你也可以指导我使用更新版本的标准。

c++ c-preprocessor preprocessor
1个回答
0
投票

这是由C++语言定义的。仅当其名称后面的非空白字符是

(
时,类似函数的宏才会被其定义替换。

翻译的第四阶段(“编译”):

[lex.phases]/4

执行预处理指令,扩展宏调用,并执行

_Pragma
一元运算符表达式。

有关预处理指令的定义和规则是相关的:

[cpp.replace.general]/12

表单的预处理指令

# define identifier lparen identifier-list_opt) replacement-list new-line
# define identifier lparen ... ) replacement-list new-line
# define identifier lparen identifier-list , ... ) replacement-list new-line

定义一个带有参数的类似函数的宏,其用法在语法上与函数调用类似。参数由可选的标识符列表指定。 类似函数的宏名称的每个后续实例,后跟

(
作为下一个预处理标记,引入了由定义中的替换列表替换的预处理标记序列(宏的调用)。替换的预处理标记序列由匹配的 ) 预处理标记终止,跳过中间匹配的左括号和右括号预处理标记对。在构成类函数宏调用的预处理标记序列中,换行符被视为普通的空白字符。

© www.soinside.com 2019 - 2024. All rights reserved.