printf的包装
我在Arduino下编码,我想开发串行打印格式化function,所以我试图使用未知大小的缓冲区的sprintf
。 基本上,我们可以避免谈论Arduino及其串行输出,并考虑将文本写入缓冲区然后使用printf
打印它。 我试过这个:
#include #include void printf0( const char* format, ... ) { va_list args; va_start(args, format); vprintf(format, args); va_end( args ); } void printf1(const char* format,...) { va_list args; va_start(args, format); char buf[vsnprintf(NULL, 0, format, args)]; sprintf(buf, format, args); printf(buf); va_end(args); } int main() { printf0("Hello, %d!\n", 15); printf1("Hello, %d!\n", 15); return 0; }
printf0
函数是我在这里找到的一个准确的例子。 我的尝试是函数printf1
,它产生不可预测的数字。 上述程序的示例输出是:
Hello, 15! Hello, 860799736!
args
是一个va_list
,所以你不能用它来调用sprintf
。 你必须使用vsprintf
或vsnprintf
:
sprintf(buf, format, args);
应该
vsnprintf(buf, sizeof buf, format, args);
此外,您应该为字符串的0终止符添加1到buf
的大小:
char buf[vsnprintf(NULL, 0, format, args) + 1];
似乎第一次调用 vsnprintf
改变args
,所以你必须添加
va_end(args); va_start(args, format);
两个电话之间: http : //ideone.com/5YI4Or
似乎对vsnprintf
的第一次调用改变了args
,但你不应该两次调用va_start
。 你应该使用va_copy
,所以添加
va_list args2; va_copy(args2, args);
在初始化args
。 另外不要忘记调用va_end(args2);
太:
链接到va_copy
手册页: https : va_copy