格式化数字打印输出

之前您看到了使用printprintln方法将字符串 打印到标准输出(System.out)。由于所有数字都可以转换为字符串(如本类后面所述),因此您可以使用这些方法来打印出字符串 和数字的任意混合形式。但是,Java 编程语言还有其他方法,当包含数字时,允许您对打印输出进行更多控制。

printf 和格式方法

java.io软件包包括PrintStream类,该类具有两种格式化方法,可用于替换printprintlnformatprintf这些方法彼此等效。您一直在使用的熟悉的System.out恰好是PrintStream对象,因此您可以在System.out上调用PrintStream方法。因此,您可以在代码中以前使用printprintln的任何地方使用formatprintf。例如,

System.out.format(.....);

这两个java.io.PrintStream方法的语法相同:

public PrintStream format(String format, Object... args)

其中format是指定要使用的格式的字符串,而args是要使用该格式打印的变量的列表。一个简单的例子是

System.out.format("The value of " + "the float variable is " +
     "%f, while the value of the " + "integer variable is %d, " +
     "and the string is %s", floatVar, intVar, stringVar);

第一个参数format是格式字符串,它指定如何格式化第二个参数args中的对象。格式字符串 包含纯文本以及格式说明符,它们是格式化Object... args的参数的特殊字符。 (符号Object... args称为* varargs *,这意味着参数的数量可能会有所不同.)

格式说明符以百分号(%)开头,以转换器结尾。转换器是一个字符,指示要格式化的参数的类型。在百分号(%)和转换器之间,您可以具有可选的标志和说明符。 java.util.Formatter中记录了许多转换器,标志和说明符。

这是一个基本示例:

int i = 461012;
System.out.format("The value of i is: %d%n", i);

%d指定单个变量是十进制整数。 %n是与平台无关的换行符。输出为:

The value of i is: 461012

printfformat方法已重载。每个版本都有以下语法:

public PrintStream format(Locale l, String format, Object... args)

例如,要在法语系统中打印数字(使用逗号代替浮点数的英语表示形式中的小数位),可以使用:

System.out.format(Locale.FRANCE,
    "The value of the float " + "variable is %f, while the " +
    "value of the integer variable " + "is %d, and the string is %s%n", 
    floatVar, intVar, stringVar);

An Example

下表列出了表后面的示例程序TestFormat.java中使用的一些转换器和标志。

  • TestFormat.java中使用的转换器和标志*
ConverterFlagExplanation
d 十进制整数。
f A float.
n 适合于运行应用程序的平台的换行符。您应该始终使用%n而不是\n
tB 日期和时间转换-特定于语言环境的月份的全名。
td, te 日期和时间转换-2 位数的月份。 td 根据需要具有前导零,te 没有。
ty, tY 日期和时间转换-ty = 2 位数字年份,tY = 4 位数字年份。
tl 日期和时间转换-12 小时制中的小时。
tM 日期和时间转换-以 2 位数字表示的分钟,必要时带有前导零。
tp 日期和时间转换-特定于区域的 am/pm(小写)。
tm 日期和时间转换-以 2 位数字表示的月份,必要时带有前导零。
tD 日期和时间转换-日期为%tm%td%ty
08八个字符的宽度,必要时带有前导零。
+包括正负号的符号。
,包括特定于语言环境的分组字符。
-Left-justified..
.3小数点后三位。
10.3右对齐十个字符,小数点后三位。

以下程序显示了您可以使用format进行的某些格式设置。输出显示在嵌入式 注解 的 Double 引号中:

import java.util.Calendar;
import java.util.Locale;

public class TestFormat {
    
    public static void main(String[] args) {
      long n = 461012;
      System.out.format("%d%n", n);      //  -->  "461012"
      System.out.format("%08d%n", n);    //  -->  "00461012"
      System.out.format("%+8d%n", n);    //  -->  " +461012"
      System.out.format("%,8d%n", n);    // -->  " 461,012"
      System.out.format("%+,8d%n%n", n); //  -->  "+461,012"
      
      double pi = Math.PI;

      System.out.format("%f%n", pi);       // -->  "3.141593"
      System.out.format("%.3f%n", pi);     // -->  "3.142"
      System.out.format("%10.3f%n", pi);   // -->  "     3.142"
      System.out.format("%-10.3f%n", pi);  // -->  "3.142"
      System.out.format(Locale.FRANCE,
                        "%-10.4f%n%n", pi); // -->  "3,1416"

      Calendar c = Calendar.getInstance();
      System.out.format("%tB %te, %tY%n", c, c, c); // -->  "May 29, 2006"

      System.out.format("%tl:%tM %tp%n", c, c, c);  // -->  "2:34 am"

      System.out.format("%tD%n", c);    // -->  "05/29/06"
    }
}

Note:

本节中的讨论仅涵盖formatprintf方法的基础。在 Essential 路径的“格式”页面的Basic I/O部分中可以找到更多详细信息。
Strings介绍了使用String.format创建字符串。

DecimalFormat 类

您可以使用java.text.DecimalFormat类来控制前零和后零,前缀和后缀,分组(千位)分隔符和十进制分隔符的显示。 DecimalFormat在数字格式设置方面提供了很大的灵 Active,但可以使您的代码更复杂。

以下示例通过将 Pattern 字符串 传递给DecimalFormat构造函数来创建DecimalFormat对象myFormatterDecimalFormat继承自NumberFormatformat()方法,然后由myFormatter调用-它接受double值作为参数,并以字符串 形式返回格式化的数字:

这是一个示例程序,说明了DecimalFormat的用法:

import java.text.*;

public class DecimalFormatDemo {

   static public void customFormat(String pattern, double value ) {
      DecimalFormat myFormatter = new DecimalFormat(pattern);
      String output = myFormatter.format(value);
      System.out.println(value + "  " + pattern + "  " + output);
   }

   static public void main(String[] args) {

      customFormat("###,###.###", 123456.789);
      customFormat("###.##", 123456.789);
      customFormat("000000.000", 123.78);
      customFormat("$###,###.###", 12345.67);  
   }
}

输出为:

123456.789  ###,###.###  123,456.789
123456.789  ###.##  123456.79
123.78  000000.000  000123.780
12345.67  $###,###.###  $12,345.67

下表说明了输出的每一行。

  • DecimalFormat.java输出*
ValuePatternOutputExplanation
123456.789###,###.###123,456.789井号(#)表示一个数字,逗号是分组分隔符的占位符,句点是十进制分隔符的占位符。
123456.789###.##123456.79value小数点右边有三位数,而pattern只有两位。 format方法通过四舍五入来处理此问题。
123.78000000.000000123.780pattern指定前导零和尾随零,因为使用 0 字符代替了井号(#)。
12345.67$###,###.###$12,345.67pattern中的第一个字符是美元符号($)。请注意,它紧接在格式output中最左边的数字之前。