无法解析条件编译 block 内的类函数宏

标签 c macros c-preprocessor conditional-compilation define-syntax

考虑以下 - 我想检查 #if #endif 是否 token 在代码中的某处定义。 我正在使用 CONCAT(input) 宏,它应该粘附我要检查的 token 的常量和变化部分。

不幸的是,下面介绍的方法会导致编译错误:

错误:标记“(”前缺少二元运算符


我找到了可以放在 #if #endif block 中的表达式:

https://gcc.gnu.org/onlinedocs/cpp/If.html#If

显然它指出:

宏。在表达式值的实际计算开始之前,表达式中的所有宏都会展开。

原来应该解析(CONCAT(test)),结果没有。

是否有任何解决方法允许在条件编译 block 中正确解析连接的标记名称?

#include <stdio.h>

#define CONCAT(input) string##input
#define stringtest 1

int main(void) 
{
    #if defined(CONCAT(test)) && (CONCAT(test)==1)
        printf("OK");
    #else
        printf("NOT");
    #endif

    return 0;
}

最佳答案

如果您只使用:#if CONCAT(test) == 1 它将起作用并且足够了。 #if defined(CONCAT(test)) 语句起作用,因为CONCAT(test) 将被评估为stringtest 将计算为 1,并且您不能对数字常量使用 defined

A different situation came to my mind - what if I want to check whether the token is eg. != 1 Then if it is not defined anywhere, the condition will evaluate to true. So there would be no difference between token not defined and token being different than 1.

您可以处理 == 0 equal to not defined。因此,您可以使用:#if CONCAT(test) != 0 && CONCAT(test) != 1 其中 CONCAT(test) != 0 表示 已定义(连接(测试))。这是唯一的选择,因为您无法在 #ifdef#if defined() 语句中进行宏扩展,请参阅 question这与你的非常相似。


gcc documentation说:

Conditionals written like this: #if defined BUFSIZE && BUFSIZE >= 1024

can generally be simplified to just #if BUFSIZE >= 1024, since if BUFSIZE is not defined, it will be interpreted as having the value zero.

此外,如果您使用 gcc -E yourSource.cpp 检查宏扩展,它也会很有帮助。

gcc --help:

-E Preprocess only; do not compile, assemble or link

关于无法解析条件编译 block 内的类函数宏,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44434458/

相关文章:

c - cpp 和 gcc -E 的区别

使用 MPI_Type_create_subarray 发送时可以转置数组吗?

c - 如何保存typeof的结果?

c++ - C++ 错误代码样板的模板与宏

c++ - 使用模板的 GoogleTest

c++ - 模板参数计算

java - 调用由 SWIG 生成的 JNI 的 UnsatisfiedLinkError?

c - scanf 函数在 GCC ubuntu 上不起作用

c - 字符串与宏的连接

scala 宏生成隐式