Java数字格式化NumberFormat详解

Java中可以使用NumberFormat对数字格式化,NumberFormat支持多种格式化模式,包含默认、百分比、货币,并且还支持指定地区,因为不同地区数字格式和货币表示方式是不同的。

NumberFormat是一个抽象类,根据Java的规则,抽象类不能被实例化,也就是不能直接new出来使用的,所以要使用NumberFormat都是使用getInstanceXXX()方法,来获取一个实例。

并且,这个实例也不是NumberFormat,因为这是个抽象类,定义一个Instance方法难道就能创建实例了吗?肯定不是,而是在这个Instance方法中创建了继承了NumberFormat的子类,看下面的源码:

//方法一,根据参数,决定创建哪种支持模式的NumberFormat
private static NumberFormat getInstance(LocaleProviderAdapter adapter,
                                            Locale locale, int choice) {
	NumberFormatProvider provider = adapter.getNumberFormatProvider();
	NumberFormat numberFormat = null;
	switch (choice) {
	case NUMBERSTYLE:
		numberFormat = provider.getNumberInstance(locale);
		break;
	case PERCENTSTYLE:
		numberFormat = provider.getPercentInstance(locale);
		break;
	case CURRENCYSTYLE:
		numberFormat = provider.getCurrencyInstance(locale);
		break;
	case INTEGERSTYLE:
		numberFormat = provider.getIntegerInstance(locale);
		break;
	}
	return numberFormat;
}

//这里最终创建了一个DecimalFormat,DecimalFormat继承自NumberFormat
private NumberFormat getInstance(Locale var1, int var2) {
	if (var1 == null) {
		throw new NullPointerException();
	} else {
		LocaleProviderAdapter var3 = LocaleProviderAdapter.forType(this.type);
		String[] var4 = var3.getLocaleResources(var1).getNumberPatterns();
		DecimalFormatSymbols var5 = DecimalFormatSymbols.getInstance(var1);
		int var6 = var2 == 4 ? 0 : var2;
		DecimalFormat var7 = new DecimalFormat(var4[var6], var5);
		if (var2 == 4) {
			var7.setMaximumFractionDigits(0);
			var7.setDecimalSeparatorAlwaysShown(false);
			var7.setParseIntegerOnly(true);
		} else if (var2 == 1) {
			adjustForCurrencyDefaultFractionDigits(var7, var5);
		}

		return var7;
	}
}

来看看使用demo

import java.text.NumberFormat;
import java.text.ParseException;

/**
 * NumberFormat使用
 */
public class TestNumberFormatErrorDemo {

    public static void main(String[] args) throws ParseException {
        NumberFormat nf = NumberFormat.getInstance();
        System.out.println(nf.getCurrency());
        System.out.println(nf.getMaximumFractionDigits());
        System.out.println(nf.getMinimumFractionDigits());
        System.out.println(nf.getMaximumIntegerDigits());
        System.out.println(nf.getMinimumIntegerDigits());
        System.out.println(nf.getRoundingMode());

        System.out.println(NumberFormat.getPercentInstance().getRoundingMode());
        System.out.println(NumberFormat.getNumberInstance().getRoundingMode());
        System.out.println(NumberFormat.getCurrencyInstance().getRoundingMode());

        /*
        CNY
        3
        0
        2147483647
        1
        HALF_EVEN
        HALF_EVEN
        HALF_EVEN
        HALF_EVEN
         */

        NumberFormat nf2 = NumberFormat.getPercentInstance();
        NumberFormat nf3 = NumberFormat.getCurrencyInstance();

        double d1 = 123456.1234567890123;
        System.out.println(nf.format(d1));
        //123,456.123

        System.out.println(nf2.format(d1));
        //12,345,612%

        System.out.println(nf3.format(d1));
        //¥123,456.12

        //设置最大小数位数为3位
        nf.setMaximumFractionDigits(3);
        System.out.println(nf.format(d1));
        //123,456.123

        double d2 = 123456.12;
        System.out.println(nf.format(d2));
        //123,456.12

        //设置最小小数位数为5位
        nf.setMinimumFractionDigits(5);
        System.out.println(nf.format(d2));
        //123,456.12000


        Number p1 = nf.parse("100");
        System.out.println(p1.intValue());

        //Unparseable number: "¥123,456.12"
        Number p2 = nf.parse("¥123,456.12");
        System.out.println(p2);

    }
}
/*
CNY
3
0
2147483647
1
HALF_EVEN
HALF_EVEN
HALF_EVEN
HALF_EVEN
123,456.123
12,345,612%
¥123,456.12
123,456.123
123,456.12
123,456.12000
100
 */