Print printf tips in debug logs

Source: Internet
Author: User
Tags variadic
Objective:

When we write programs, we always add some statements like printf to output debugging information, but the printf statement has a very inconvenient place when we need to publish a program to delete these statements, and once you need to debug again, These statements have to add, which brings us a lot of inconvenience, wasting our time, but also caused the inefficient commissioning. Therefore, many people choose to use the macro definition to output the debug statements.

For example, define a macro switch:

#define __debug

When debugging is required, use the statement:

#ifdef __debug

printf (XXX);

#endif

Debugging this way, you can tell the compiler not to compile these statements by undef __debug, so that the statements are no longer exported. But this way of trouble is also obvious, each debug statement needs to use two macro definition to surround, this not only in the code to write inconvenient, the source code structure is not good to see, the workload is still not small.

If we were able to program these three sentences, it would be so much more comfortable, so we thought of using such a statement:

#ifdef __debug

#define DEBUG (Info) printf (info)

#else

#define DEBUG (Info)

#endif

Thus, when we write the code, we can use debug a statement, we open the macro switch __debug, all the debug (info) macro definition information will be replaced with printf (info), closed will be replaced by empty, so it will not be compiled. Well, this time more convenient, a statement on it ~ ~ ~ However, the problem comes with it, printf is to support multiple parameters, and is an indeterminate parameter, when you use the following statement will be an error:

DEBUG ("%s", msg)

This is because the DEBUG (info) macro definition only supports the substitution of one parameter.

So, we want debug to be able to support multiple parameters like printf, and these parameters just expand into the parameters used by the printf statement itself, such as: We want Debug ("%s", msg) to be expanded to printf ("%s", msg)

Text:

Through the online data access, found since the C99 specification, the compiler began to support the indefinite parameter macro definition, like printf.

You can take a look at this article: http://blog.csdn.net/aobai219/archive/2010/12/22/6092292.aspx

(this link also turns, I have not found the original author who is, alas, the Internet ah ...) )

So, we define a kind of stuff like this:

#define DEBUG (format, ...) printf (format, # #__VA_ARGS__) (' # # ' means that if the mutable parameter is ignored or empty, the preprocessor (preprocessor) is removed from the comma in front of it. )

So, we magically discovered that debug completely replaced printf, all of the debug (...) have been replaced by printf (...) and will never be bothered by that hateful comma.

However, we found that the light has printf is not enough, although debugging information is output, but a lot of debugging information output, we can not immediately know where this information is printed out in the end, so, we would like to, can the current file name and source line location also print it? This is not at a glance, where still use to think, to find debugging information where the output, have been printed out.

So we have the following story ...

compiler built-in macros:

We first introduce several compiler built-in macro definitions, these macro definitions can not only help us to complete the cross-platform source code writing, flexible use can also skillfully help us to output very useful debugging information.

There are several standard scheduled macros (also commonly used) in the ANSI C standard:

__LINE__: Inserts the current source code line number in the source code;

__FILE__: Inserts the current source filename in the source file;

__DATE__: Insert the current compilation date in the source file

__TIME__: Inserts the current compile time in the source file;

__STDC__: The identifier is assigned a value of 1 when the program strictly complies with the ANSI C standard;

__cplusplus: This identifier is defined when you write a C + + program.

The compiler will automatically replace these macros with the corresponding content when compiling the source code.

See here, your eyes should be bright now, eh, yes, __file__ and __line__ is exactly what we want in front of the output, so, each of our statements has become:

DEBUG ("FILE:%s, line:%d ...", __file__,__line__,...)

In fact, there is no need, __file__ itself will be replaced by the compiler to character constants, so our statement has become this:

DEBUG ("FILE:" __file__ ", Line:%d ...", __line__,...)

However, we are still not satisfied, still find, still very annoying, why each statement to write "FILE:" __file__ ", Line:%d and, __line, the two parts of it." This is not a waste of our time.

Haha, yes, this is the big finale, the debug is written like this:

DEBUG (Format,...) printf ("FILE:" __file__ ", Line:%d:" format "/n", __line__, # #__VA_ARGS__)

Yes, that's it. Below, all the debug information will be output in this way:

File:xxx, Line:xxx, ...

finally:

Finally, the ritual, coding test.

View plain 10 20 30 40 50 60 70 80 90 100 110 120 130 140 //============================================================================  // Name  : debug.cpp  // author : boyce  // version : 1.0   // copyright : pku  // description : hello world  in C++, Ansi-style  //============================================================== ==============   #include    #define  __DEBUG__   #ifdef  __DEBUG__    #define  DEBUG (format,...)  printf ("file: " __file__ ", line: %05d: " format "/n",  __line__, # #__VA_ARGS__ )    #else    #define  DEBUG (format,...)    #endif    int main ()  {        char str[]= "Hello world";       debug ("A ha, check  me: %s ", str);       return 0;  }    

Test results:

Does it feel cool? O (∩_∩) o haha

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

Passing variable parameter tables with variable-parameter macros (Variadic macros)

You may be familiar with the use of variable parameter tables in functions such as:
void printf (const char* format, ...);

Until recently, a mutable parameter table could only be applied to a real function and could not be used in a macro.

The C99 compiler standard has finally changed this situation, allowing you to define variable parameter macros (Variadic macros) so that you can use a macro that has a parameter table that can be changed. The variable-parameter macro looks like this:

#define DEBUG (...) printf (__va_args__)

The default number represents a table of parameters that can be changed. Use the reserved name __va_args__ to pass parameters to the macro. When the macro's call is expanded, the actual parameters are passed to printf (). For example:

Debug ("y =%dn", y);

The processor replaces the macro call with the following:

printf ("y =%dn", y);

Because Debug () is a variable parameter macro, you can pass a different number of arguments in each call:

Debug ("Test"); A parameter

Variable parameter macros are not officially supported by Ansi/iso C + +. Therefore, you should check your compiler to see if it supports this technology

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.