背景:我有许多脚本通过查找前导"0x"来解析查找十六进制数字的日志文件.我们的嵌入式C库改为新的printf.新的printf比我们之前更符合标准,我的脚本破了.
在Linux机器上:
#include <stdio.h>
int main( void )
{
printf( "%#010x\n", 0 );
printf( "%#010x\n", 1 );
return 0;
}
Run Code Online (Sandbox Code Playgroud)
输出(使用glibc)是:
0000000000
0x00000001
Run Code Online (Sandbox Code Playgroud)
我们公司的输出是:
0x00000000
0x00000001
Run Code Online (Sandbox Code Playgroud)
从printf(3)开始,在'#'标志字符上:"对于x和X转换,非零结果的前缀为字符串"0x"(或X转换为"0X")."
我很好奇为什么.如果没有挖掘C标准文件或为标准委员会成员购买午餐,为什么不在零价值论证中使用前导0x?
Juk*_*ela 24
标准似乎是这样编写的:
%#x并%#o尝试保证可以使用strtolwith 正确解析输出base = 0.
在这些情况下,#标志会添加尽可能少的额外字符.例如,打印0表示0因为不需要添加额外的0x.如果不指定最小字段宽度和0填充,这很有意义.
如果你想0x总是添加,你通常可以简单地写一些类似的东西0x%x.因此%#x,似乎只在那些你真正想要特殊处理0的特殊情况下才有用.但是预先挂起的0x对于默认字段宽度说明符不能正常工作例如)0x%12x是由0x和十六进制之间的空格右对齐数字,在这种情况下不太可能是想要的.对于这种情况,需要使用sprintf进行额外的准备传递,因此十六进制字符串"0x2ac2"可以是白色空格右对齐,printf( "%12s", hexstr);幸运的是0使用类似于printf( "0x%012x", hexstr);工作的东西来证明解析器的有效十六进制数字.
现在%#x规定工作的方式在隔离方面很有意义.%010x指定工作的方式在孤立的情况下很有意义.你正在组合这两个修饰语,最终结果可能是奇怪的.对于另一个应用程序,比如自动生成整齐的C代码来初始化表,0,而0x0不是一个问题.
但也没有必要合并%#x和%010x.你可以写信0x%08x去做你想做的事.