C printf格式字符串

C printf格式字符串,c,printf,C,Printf,在C语言中,下列程序中有%5%%, 但我不知道怎么做 printf("%6%5%%%78%"); 这是未定义的行为,特定于编译器/平台。带有错误参数的Printf函数将开始从堆栈中剥离变量,然后任何事情都可能发生 这就是为什么编译器通常会对此抱怨的原因 source.c:5:5: warning: conversion lacks type at end of format [-Wformat] source.c:5:5: warning: conversion lacks type at

在C语言中,下列程序中有%5%%, 但我不知道怎么做

 printf("%6%5%%%78%");

这是未定义的行为,特定于编译器/平台。带有错误参数的Printf函数将开始从堆栈中剥离变量,然后任何事情都可能发生

这就是为什么编译器通常会对此抱怨的原因

source.c:5:5: warning: conversion lacks type at end of format [-Wformat]
source.c:5:5: warning: conversion lacks type at end of format [-Wformat]
source.c:5:5: warning: conversion lacks type at end of format [-Wformat]
source.c:5:5: warning: spurious trailing '%' in format [-Wformat]

Printf格式字符串后面应该跟有相同数量的参数,这里显然没有这样做

printf格式字符串的可能参数有:

%[flags][width][.precision][length]specifier
其中,说明符是s表示字符串,c表示字符等。其他说明符是可选的

对于左对齐或右对齐,标志是+、-、0等中的一个,问题中不传递任何标志

precision的前缀是a.,因此在本例中它是不存在的

让我们看看

printf("%6%5%%%78%");
  • 现在%后面的第一个参数作为字段宽度,即6和 因此未打印。但是,它希望后面有一个说明符 其中又有%。标准表示%后跟%打印它 到stdout。因此,您会看到%首先打印。现在因为%的效果是 丢失,因此5被视为正常数字并打印

  • 然后我们看到%%,它将打印单个%。下一个是单曲 %,然后是78,预计为宽度,因此不打印。 然而,后一个百分比否定了78的效果,并打印了一个 单一%

为了验证上述评估,这里有一个测试字符串

printf("%6%4%3%2");
按照上述要求打印%4%2

供详细参考
这里可能发生的情况是:

  • printf实现可以看到“%6”,它可以是有效转换规范的开始,例如“%6d”
  • 然后它会看到“%”,这不再是有效的转换规范。此时,字符串不符合C标准(例如,C 1999 7.19.6.1 8规定“完整的转换规范应为%%”),实现可能会做任何事情。这个特定的实现似乎忽略了“6”,就像转换规范是“%%”,而不是“%6%”。因此,它会将“%”写入标准输出
  • 然后printf实现看到“5”,所以它写“5”
  • 然后它会看到“%%”,这是一个导致写入“%”的有效转换规范
  • 然后它会看到“%78%”。与“%6%”一样,“%78”可以启动有效的规范,但第二个“%”是错误的。实现再次忽略了“78”并写入“%”

在其他C实现中,行为会有所不同。该计划形式不合理;它不符合C标准,并且其行为未由C标准指定。

I可能是错误的,但这看起来不像是
printf
的有效格式字符串。。。对于C99§7.19.6.1¨9,“如果转换规范无效,则行为未定义”。@AxelIsouard的意思可能是“我不知道为什么”。首先,尝试运行它,然后在此处添加注释。请告诉我们您期望的输出。@AsdAsd:字符串不是有效的格式字符串。C标准要求根据C 1999 7.19.6.1 8,转换说明符“%”显示为“%”,而不是“%6%”。但是,我正在Dev编译器上运行此语句,并且它已成功运行。我是在一次考试中得到这个问题的,他们也只是在测试后才给出这个问题。@AsdAsd:“任何事情都有可能发生,而且程序格式不正确”和“它可以编译”之间没有矛盾。想一想,只要需要。这是非常重要的一点。@Asd:仅仅因为某些东西看起来运行正常,并不意味着它是正确的。如果你把这类事情当作一个试题,你可能应该考虑改一个更好的学校的课程。它的一个公司的试卷问题告诉他们行为是不明确的,为什么…这将是他们所期待的。