我遇到了以下代码,无法弄清楚它是如何工作的。
System.out.printf("17%1$s","16%1$s");
System.out.printf("17%1$s","16%1$s","18%1$s");
无论你为前两个人准备什么,都会打印相同的数字
您可以添加有多少参数printf
输出相同。
产生的输出是:1716%1$s
System.out.printf("17%1$s","16%4$s","17%1$s","20%1$s");
输出为:1716%4$s
所以我意识到它不会在第二个参数之后处理。
如果我将代码更改为
System.out.printf("17%5$s","16%4$s","17%1$s","20%1$s");
我得到java.util.MissingFormatArgumentException
???
工作原理如何?这些参数是什么? 提前致谢
答案 0 :(得分:2)
System.out.printf("17%1$s","16%1$s");
printf
的第一个参数是格式字符串。剩下的任何参数都是要打印的数据。
此处的格式字符串为"17%1$s"
。这包含一些字面上应该出现的字符,即两个字符"17"
。然后它包含一个格式说明符,指示其中一个参数应该如何出现。格式说明符始终以%
开头。
这个特殊的说明符分解如下:
% - tells printf that a format specifier is coming up
1$ - tells it to use the first argument to printf (not counting the format
string itself--so it's really the second argument)
s - tells it that the argument is expected to be a String
因此输出为"17"
,后跟参数,即字符串"16%1$s"
。虽然参数看起来也有格式说明符,但实际上并非如此。除第一个之外的所有参数都只是数据。
如果添加其他参数,它们不会影响printf
的输出,因为格式字符串中没有格式说明符(即第一个告诉printf
使用它们。
System.out.printf("17%5$s","16%4$s","17%1$s","20%1$s");
这里,格式字符串告诉printf
使用第五个数据参数,而不是计算格式字符串本身。由于没有第五个数据参数(只有三个),因此会出现异常。
(PS您不需要在格式字符串中包含1$
。如果缺少,则第一个格式说明符自动使用第一个数据参数,第二个格式说明符使用第二个数据参数,并且等等。)
格式字符串的语法描述为here。
答案 1 :(得分:1)
请查看此文档:
Formatting Numeric Print Output
你所拥有的内容与Java的日期格式非常相似(虽然不相关)。 该链接中的表格应该让您更清楚。
编辑:对不起,忘了另一个更重要的链接答案 2 :(得分:1)
System.out.printf(...)
遵循Formatter
类的语法,它不会递归处理。第一个参数是要进行替换的参数,其余的只是要在第一个字符串中替换的值。
替换的说明符遵循以下模式:
%[argument_index$][flags][width][.precision]conversion
在System.out.printf("17%1$s","16%1$s");
的情况下,它替换了第一个字符串中的“%1 $ s”
使用“16%1 $ s”,“%1 $ s”表示“语法字符串(1 $)后面的第一个参数,其转换是字符串类型(末尾的's')”)如果您的方法包含比第一个字符串中指定的参数多,它们只是被忽略。
此处有更多信息:http://docs.oracle.com/javase/1.5.0/docs/api/java/util/Formatter.html