C 宏中的变量参数

C 宏中的变量参数,c,macros,visual-c++,variadic-functions,C,Macros,Visual C++,Variadic Functions,我有一个接受变量参数的函数,如下所示 int log_data (LOG_TYPE eType, ...) { /** some logging related stuff here **/ } 在头文件中,我使用 #ifdef LOGGING_ENABLED int log_data (int nType, ...); #else #define log_data(_x_, ...) #endif 基本上,这个想法是打开和关闭调试~~~ 问题: 上述逻辑在Linux和gcc中工作

我有一个接受变量参数的函数,如下所示

int log_data (LOG_TYPE eType, ...)
{
    /** some logging related stuff here **/
}
在头文件中,我使用

#ifdef LOGGING_ENABLED
int log_data (int nType, ...);
#else
#define log_data(_x_, ...)
#endif
基本上,这个想法是打开和关闭调试~~~

  • 问题: 上述逻辑在Linux和gcc中工作得非常好,但在Windows VC++中编译时出错

旧版本的VC++不支持宏中的变量参数

您可以使用此技巧绕过它:

#ifdef LOGGING_ENABLED
#define log_data log_data_impl
#else
#define log_data
#endif

// usage:
log_data(level, ...)
更新-另一种可能的解决方法:

#ifdef LOGGING_ENABLED
#define log_data(P) log_data_impl P // no braces around P!
#else
#define log_data(P)
#endif

// usage: we have to use two braces
log_data((level, ...));

变量宏是比较新的,例如:“支持VC++中的变量宏的引入。”您可能有一个较旧的版本。

编辑:如果要调试,则声明
log\u数据
,如果不想调试,则不声明。这意味着您在
#ifdef
中也有函数的定义。只要您这样做,解决方案就是:

int log_data (int nType, ...)
{
#ifdef LOGGING_ENABLED
     /* the code to do logging */
#else
     return 0; /* or whatever */
#endif
}
在头文件中,像往常一样声明函数:

int log_data (int nType, ...);
这有一个缺点,即即使在不记录日志的情况下也存在函数调用,但优点是它在没有预处理器支持varargs的情况下也能工作。

说“VC++不支持…”这句话是不明确的。例如,它在更高版本上确实支持它。您可以只说
#ifdef LOGGING_DISABLED#define log_data#endif
,然后所有对
log_data(x,y,z)
的调用都将转换为
(x,y,z)
,并在无效上下文中进行计算,但如果参数有副作用,这将不起作用(为了记录在案,他们可能不应该这么做。)任何合理的现代编译器都应该优化掉这个“缺点”。