问题提出

有时候我们想用宏定义来决定是编译debug版本的代码还是release的代码,dubug版本的代码会通过printf打印调试信息,release版本的代码则不会。我们总不能对每一条printf都这样写:

 #if _DEBUG_
printf("hello world!");
#endif

这样子实在是太麻烦了!万一要各个地方都要打印,会使版面看起来很乱。

解决方法

我后来想到一个方法,可以使用宏定义代替printf函数,由于printf是可变参数的函数,这里就要用到变參宏(…和__VA_ARGS__)。 
在头文件下写此代码

 #define _DEBUG_ 1

 #if _DEBUG_
#define PR(...) printf(__VA_ARGS__)
#else
#define PR(...)
#endif

后面需要打印调试信息的时候使用PR宏就可以了,如果需要release版本,不打印调试信息,就把DEBUG设置为0,编译出来的程序就不会打印调试信息了。

示例代码清单

开发环境VS2013。当DEBUG设置为1,打印PR的信息;当DEBUG设置为0,不打印PR的信息。

 #include "stdafx.h"

 #define _DEBUG_ 1

 #if _DEBUG_
#define PR(...) printf(__VA_ARGS__)
#else
#define PR(...)
#endif int _tmain(int argc, _TCHAR* argv[])
{ printf("debug test!\r\n"); PR("hello world!\r\n");
PR("string:%s\r\n", "data");
PR("integer:%d\r\n", ); return ;
}

提醒

该技巧可以用在单片机C语言开发上,切换版本非常方便。 
keil环境下如何重定向printf到串口,可以参考这里

来源

【转】用宏定义代替printf函数的更多相关文章

  1. 用宏定义代替printf函数

    来自:http://blog.csdn.net/yannanxiu/article/details/52506451 #define _DEBUG_ 1 #if _DEBUG_ #define PR( ...

  2. #define宏定义形式的"函数"导致的bug

    定义了一个宏定义形式的"函数": #define  SUM8(YY)\ {\ int Y = YY>>2;\ ...\ } 然后使用的时候,传入了一个同名的变量Y: i ...

  3. C++内联函数、宏定义和普通函数的区别

    C++内联函数.宏定义和普通函数的区别? 宏定义:在预处理阶段进行简单的文本替换,不会进行参数类型检查: 内联函数:在编译器的时候进行代码插入,编译器会在每次调用内联函数的地方直接将内联函数的内容展开 ...

  4. C 语言宏定义函数编写时 do-while 的妙用和一些注意事项

    在 C 语言中,我们都知道可以用宏定义来编写函数,一般称为宏函数.如果一个宏函数比较复杂,那么在编写这样的宏函数是有一定技巧和注意事项的.文章给出一些我认为值得关注的地方,以及一些注意事项(个人建议) ...

  5. 【C++】函数指针宏定义

    看耗子叔文章学习虚函数表(http://blog.csdn.net/haoel/article/details/1948051)的时候被例子的第一句惊到了 typedef void(*Fun)(voi ...

  6. (转载)内联函数inline和宏定义

    (转载)http://blog.csdn.net/chdhust/article/details/8036233 内联函数inline和宏定义   内联函数的优越性: 一:inline定义的类的内联函 ...

  7. 【C++】内联函数(inline)和宏定义(# define)的优劣及其区别

    一.宏定义:# define 1.为什么要使用宏? 因为调用宏比调用函数更有效率,函数的调用必须要将程序的执行顺序转移到函数所存放的内存地址中,将函数程序内容执行完后,再返回到执行该函数前的地方,这种 ...

  8. 黑马程序员——C语言基础 枚举 宏定义 自定义 static exterm

    Java培训.Android培训.iOS培训..Net培训.期待与您交流! (以下内容是对黑马苹果入学视频的个人知识点总结) (一)枚举 1)枚举类型的定义 枚举是C语言中的一种基本数据类型,并不是构 ...

  9. C Program基础-宏定义

    写好c语言,漂亮的宏定义是非常重要的,我们在阅读别人工程时,往往能看到大量的宏定义,宏定义可以增加代码的可读性,也能增加代码的可移植性,一个好的宏定义甚至是一件艺术品.今天我们就来看看宏定义的方方面面 ...

随机推荐

  1. mysql 常用的几个函数

    IF 函数 语法:`IF`(expr1,expr2,expr3); 当expr1为ture时,值为expr2,当expr1为false时,值为expr3. 如: IFNULL 函数 语法:IFNULL ...

  2. 开发CMDB系统

    背景: 在现网环境中服务器多了每天服务器的配置 情况我们很难记住,当某台服务器硬件配置变化后可以第一时间了解,某台服务器出现问题时可以快速定位机架位置,之前都是excel文档,要查某项数据时极不方便. ...

  3. Git的学习与使用

    Git使用教程 一:Git是什么? Git是目前世界上最先进的分布式版本控制系统. 二:SVN和Git最主要的区别? SVN是集中式版本控制系统,版本库是集中放在中央服务器的,而干活的时候,用的都是自 ...

  4. LInux下设置账号有效时间 以及 修改用户名(同时修改用户组名和家目录)

    在linux系统中,默认创建的用户的有效期限都是永久的,但有时候,我们需要对某些用户的有效期限做个限定!比如:公司给客户开的ftp账号,用于客户下载新闻稿件的.这个账号是有时间限制的,因为是付费的.合 ...

  5. zabbix监控交换机、防火墙等网络设备

    zabbix3.4.4监控交换机/防火墙是非简单,只需知道交换机/防火墙的snmp密码,然后连接下自带或导入的snmp模板,就可以完成监控了.比如添加地址为172.10.11.5的交换机监控. 1)登 ...

  6. C_数据结构_数组

    //数组 # include <stdio.h> # include <malloc.h> //包含了 malloc 函数 # include <stdlib.h> ...

  7. Oracle系列(三): 情景查询一 a表中有个fid字段,逗号分隔开来,b表中有id字段及其他信息,如何关联a表的fid和和b表的id字段查询

    现在有两个表,表a中 DOC FID 1 a,b,c 2 a,c,d 表b中 ID KEY a A b B c C d D 怎么联合查询出 DOC FID KEY 1 a,b,c A,B,C 2 a, ...

  8. jquery打印页面(jquery.jqprint)

    使用jquery进行打印时,所需js包:jquery-1.4.4.min.js.jquery.jqprint-0.3.js 但如果使用高版本的jquery(jquery-1.9.1.min.js)时, ...

  9. Maven -Maven配置tomcat插件 两种

    Maven Tomcat插件现在主要有两个版本,tomcat-maven-plugin和tomcat7-maven-plugin,使用方式基本相同. tomcat-maven-plugin 插件官网: ...

  10. mac安装VMware虚拟机(含序列号)及Ubuntu系统

    首先去官网下载虚拟机,这里下载vmware fusion 10的版本: https://www.vmware.com/products/fusion/fusion-evaluation.html 下载 ...