C ++宏不能代替?

时间:2015-08-04 04:11:18

标签: c++ macros

这是代码。

#include <iostream>
using namespace std;

#define gao falsegao
#define fun(entity) \
    void fun_##entity() \
    {                     \
        std::cout << #entity << std::endl; \
    }

fun(gao);

int main()
{
    fun_gao();
    return 0;
}

该程序将编译并轻松运行。但为什么?我已将gao定义为falsegao,生成的函数不应为void fun_false_gao()吗?输出也应该是false_gao

请帮助我解决这个难题,何时进行替换?这背后的原理是什么?

2 个答案:

答案 0 :(得分:1)

您需要一个两级fun

#define fun_(entity) \
    void fun_##entity() \
    {                     \
        std::cout << #entity << std::endl; \
    }

#define fun(entity) fun_(entity) 

这将按预期工作。

C ++语言的宏替换规则阻止预处理器递归替换与###运算符相邻的标记中的宏名称。您需要额外级别的“隔离”,以确保gao在到达falsegao##之前被# 替换。

答案 1 :(得分:1)

不,##运算符的优先级高于参数替换。惯用它包裹在宏中:

#define CAT_LITERAL( A, B ) A ## B
#define CAT( A, B ) CAT_LITERAL( A, B )

同样适用于#运算符。

#define STR_LITERAL( LIT ) # LIT
#define STR( PARAM ) STR_LITERAL( PARAM )

所以定义了你的宏:

#define fun(entity) \
    void CAT( fun_, entity ) () \
    {                     \
        std::cout << STR( entity ) << std::endl; \
    }