预处理命令

http://www.uml.org.cn/c++/200902104.asp

#define              定义一个预处理宏
#undef               取消宏的定义

#include            包含文件命令
#include_next   与#include相似, 但它有着特殊的用途

#if                      编译预处理中的条件命令, 相当于C语法中的if语句
#ifdef                判断某个宏是否被定义, 若已定义, 执行随后的语句
#ifndef             与#ifdef相反, 判断某个宏是否未被定义
#elif                  若#if, #ifdef, #ifndef或前面的#elif条件不满足, 则执行#elif之后的语句, 相当于C语法中的else-if
#else                与#if, #ifdef, #ifndef对应, 若这些条件不满足, 则执行#else之后的语句, 相当于C语法中的else
#endif              #if, #ifdef, #ifndef这些条件命令的结束标志.
defined            与#if, #elif配合使用, 判断某个宏是否被定义

#line                标志该语句所在的行号
#                      将宏参数替代为以参数值为内容的字符窜常量
##                   将两个相邻的标记(token)连接为一个单独的标记
#pragma        说明编译器信息

#warning       显示编译警告信息
#error            显示编译错误信息

--------------------------------------

http://www.cnblogs.com/clover-toeic/p/3851102.html

2.3.2.4 可变参数宏

     ...在C语言宏中称为Variadic Macro,即变参宏。C99编译器标准允许定义可变参数宏(Macros with a Variable Number of Arguments),这样就可以使用拥有可变参数表的宏。

     可变参数宏的一般形式为:

                        #define  DBGMSG(format, ...)  fprintf (stderr, format, __VA_ARGS__)

     省略号代表一个可以变化的参数表,变参必须作为参数表的最右一项出现。使用保留名__VA_ARGS__ 把参数传递给宏。在调用宏时,省略号被表示成零个或多个符号(包括里面的逗号),一直到到右括号结束为止。当被调用时,在宏体(macro body)中,那些符号序列集合将代替里面的__VA_ARGS__标识符。当宏的调用展开时,实际的参数就传递给fprintf ()。

     注意:可变参数宏不被ANSI/ISO C++所正式支持。因此,应当检查编译器是否支持这项技术。 

     在标准C里,不能省略可变参数,但却可以给它传递一个空的参数,这会导致编译出错。因为宏展开后,里面的字符串后面会有个多余的逗号。为解决这个问题,GNU CPP中做了如下扩展定义:

                       #define  DBGMSG(format, ...)  fprintf (stderr, format, ##__VA_ARGS__)

     若可变参数被忽略或为空,##操作将使编译器删除它前面多余的逗号(否则会编译出错)。若宏调用时提供了可变参数,编译器会把这些可变参数放到逗号的后面。

     同时,GCC还支持显式地命名变参为args,如同其它参数一样。如下格式的宏扩展:

                              #define  DBGMSG(format, args...)  fprintf (stderr, format, ##args)

     这样写可读性更强,并且更容易进行描述。

     用GCC和C99的可变参数宏, 可以更方便地打印调试信息,如:

1 #ifdef DEBUG
2     #define DBGPRINT(format, args...) 
3         fprintf(stderr, format, ##args)
4 #else
5     #define DBGPRINT(format, args...)
6 #endif

     这样定义之后,代码中就可以用dbgprint了,例如dbgprint ("aaa [%s]", __FILE__)。

     结合第4节的“条件编译”功能,可以构造出如下调试打印宏:

复制代码
 1 #ifdef LOG_TEST_DEBUG
 2     /* OMCI调试日志宏 */
 3     //以10进制格式日志整型变量
 4     #define PRINT_DEC(x)          printf(#x" = %d
", x)
 5     #define PRINT_DEC2(x,y)       printf(#x" = %d
", y)
 6     //以16进制格式日志整型变量
 7     #define PRINT_HEX(x)          printf(#x" = 0x%-X
", x)
 8     #define PRINT_HEX2(x,y)       printf(#x" = 0x%-X
", y)
 9     //以字符串格式日志字符串变量
10     #define PRINT_STR(x)          printf(#x" = %s
", x)
11     #define PRINT_STR2(x,y)       printf(#x" = %s
", y)
12 
13     //日志提示信息
14     #define PROMPT(info)          printf("%s
", info)
15 
16     //调试定位信息打印宏
17     #define  TP                   printf("%-4u - [%s<%s>]
", __LINE__, __FILE__, __FUNCTION__);
18 
19     //调试跟踪宏,在待日志信息前附加日志文件名、行数、函数名等信息
20     #define TRACE(fmt, args...)
21     do{
22         printf("[%s(%d)<%s>]", __FILE__, __LINE__, __FUNCTION__);
23         printf((fmt), ##args);
24     }while(0)
25 #else
26     #define PRINT_DEC(x)
27     #define PRINT_DEC2(x,y)
28 
29     #define PRINT_HEX(x)
30     #define PRINT_HEX2(x,y)
31 
32     #define PRINT_STR(x)
33     #define PRINT_STR2(x,y)
34 
35     #define PROMPT(info)
36 
37     #define  TP
38 
39     #define TRACE(fmt, args...)
40 #endif


复制代码

 ================================================================

上面都是摘抄,我遇到的问题是这样的

debug(fmt, args...) debug_printf(__FUNCTION__,fmt,##args)

这样是编不过的,

debug(fmt, ...) debug_printf(__FUNCTION__,fmt,##__VA_ARGS__)//buyao xiecuo xiahuaxian geshu

这样才编过

原文地址:https://www.cnblogs.com/minggoddess/p/4679855.html