我们可以使用C预处理器##操作符粘贴3个令牌吗



似乎可以定义一个宏来将3个令牌连接为:

#define concat3(a,b,c) a##b##c

a##bb##c产生的中间令牌必须是有效的预处理器令牌吗?或者是否有可能在所有一致的实现上成功粘贴concat3(.,.,.)(1(


(1(许多编译器支持..作为大小写范围的令牌,这使它成为一个有效的令牌,但C标准没有定义这个令牌,那么concat3()宏在不支持它的体系结构上会失败吗

在我看来,每个中间令牌都必须是有效的,否则就会被视为未定义的行为。我在下面引用的部分来自C11标准,但C99和C20草案中的语言似乎是相同的。

第6.10.3.3节涵盖了##运算符的实际解释,具体指的是连接的前一个和后一个令牌,即它们成对处理。第3段有点令人困惑,因为它单独提到了占位符替换(即,一个参数没有预处理标记的类似函数的宏的扩展(,然后指定";如果结果不是有效的预处理令牌,则行为是未定义的";。目前还不清楚它是指占位符大小写还是所有的串联。

然而,J.2部分确定了";预处理运算符CCD_ 7的结果不是有效的预处理令牌";作为没有条件的未定义行为,所以我认为这可能有助于澄清我的上述观点。

还要注意的是,该标准规定##运算符的求值顺序是未指定的,因此每个可能的级联组合都必须是有效的。

最新更新