java.text.Format及相关类详解

java.text.Format

Format是一个用于格式化语言环境敏感的信息(如日期、消息和数字)的抽象基类,直接已知子类有DateFormat, MessageFormat, NumberFormat。

Format定义了编程接口,用于将语言环境敏感的对象格式化为String(使用format方法)和将String重新解析为对象(使用 parseObject方法)。 
通常,一个Format的parseObject方法必须能解析任何由其Format方法格式化的字符串。不过,也可能存在不能解析的异常情况。例如,Format方法可能创建中间无分隔符的两个相邻整数,在这种情况下,parseObject无法判断哪个数字属于哪个数。

Java平台为格式化日期、消息和数字分别提供了三个特殊的Format的子类:DateFormat、MessageFormat和NumberFormat。具体的子类必须实现三个方法: 
format(Object obj, StringBuffer toAppendTo, FieldPosition pos) 
formatToCharacterIterator(Object obj) 
parseObject(String source, ParsePosition pos) 
这些常规方法允许对对象进行多态解析和格式化,还可以被使用(如被 MessageFormat 使用)。子类通常也为特定的输入类型提供了另外的format方法,也为特定的结果类型提供了parse方法。当在输入文本的开始没有任何所需格式的文本时,则任何不带 ParsePosition参数的parse方法都应该抛出ParseException。 
大多数子类还将实现以下工厂方法: 
getInstance 获取一个适合于当前语言环境的有用的格式对象 
getInstance(Locale) 获取一个适合于指定语言环境的有用的格式对象。 
此外,某些子类还可能为了更特殊的控制实现其它getXxxxInstance方法。例如,NumberFormat类提供了getPercentInstance和 getCurrencyInstance方法来获取特殊的数字格式器。
Format的子类如果允许程序员能为不同语言环境(比如用getInstance(Locale) )创建对象,必须实现以下类方法: 
public static Locale[] getAvailableLocales()
最后子类定义一个常量集合来标识格式输出中的不同字段。这些常量用于创建一个FieldPosition对象该对象标识字段中所包含的信息及其在格式化结果中的位置。这些常量应当命名为item_FIELD,其中item标识了该字段。有关这些常量的例子,请参阅 ERA_FIELD及其在DateFormat中的同类。

格式通常不是同步的。建议为每个线程创建独立的格式实例。如果多个线程同时访问一个格式,其它必须保持外部同步。

java.text.FieldPosition

构造方法

public FieldPosition(int field)

为给定字段创建一个FieldPosition对象。字段由常量标识,在不同的Format子类中,常量名称一般以_FIELD结尾。

public FieldPosition(Format.Field attribute)

为给定的字段常量创建一个FieldPosition对象。字段由不同Format子类中定义的常量来标识。这等效于调用new FieldPosition(attribute, -1)。

public FieldPosition(Format.Field attribute,int fieldID)

为给定的字段创建一个FieldPosition对象。字段由来自Field的子类之一的属性常量以及一个由Format的子类定义的整型字段ID标识。

当attribute不为null时,需要使用Field的Format子类应当优先考虑attribute而忽略fieldID。

不过,旧的Format子类可能不知道Field而依靠fieldID。如果该字段没有相应的整型常量,则fieldID应为-1。

FieldPosition是Format及其子类用于在格式输出中(format(Object obj, StringBuffer toAppendTo, FieldPosition pos))标识字段的简单类。
FieldPosition保持对格式输出中字段位置的两个索引进行跟踪:字段的第一个字符的索引和紧跟字段的最后一个字符的索引。 
不同的Format类中的format方法需要一个FieldPosition对象作为参数。使用此format方法执行部分格式化或者以获取格式化输出的信息(比如字段位置)。字段可以通过两种方式标识,两者的作用是一致的,只是Format.Field常量更详细,建议使用这种方式: 
1、通过一个其名称通常以_FIELD结尾的整型常量。这些常量在Format的不同子类中定义:

NumberFormat

static int FRACTION_FIELD
          用于构造FieldPosition对象的字段常量。
static int INTEGER_FIELD
          用于构造FieldPosition对象的字段常量。

例子:

public static void main(String[] args) {
        NumberFormat numberFormat = NumberFormat.getInstance();
        StringBuffer stringBuffer1 = new StringBuffer();
        FieldPosition fieldPosition = new FieldPosition(NumberFormat.INTEGER_FIELD);
        BigDecimal bigDecimal = new BigDecimal("1.23456789");
        stringBuffer1 = numberFormat.format(bigDecimal, stringBuffer1, fieldPosition);
        System.out.println("stringBuffer1 = " + stringBuffer1);
        System.out.println("INTEGER:beginIndex=" + fieldPosition.getBeginIndex() + ",endIndex=" + fieldPosition.getEndIndex());

        fieldPosition = new FieldPosition(NumberFormat.FRACTION_FIELD);
        StringBuffer stringBuffer2 = new StringBuffer();
        stringBuffer2 = numberFormat.format(bigDecimal, stringBuffer2, fieldPosition);
        System.out.println("stringBuffer2 = " + stringBuffer2);
        System.out.println("FRACTION:beginIndex=" + fieldPosition.getBeginIndex() + ",endIndex=" + fieldPosition.getEndIndex());
    }
stringBuffer1 = 1.235
INTEGER:beginIndex=0,endIndex=1
stringBuffer2 = 1.235
FRACTION:beginIndex=2,endIndex=5

2、通过一个Format.Field常量:

NumberFormat.Field

static NumberFormat.Field CURRENCY
          标识货币字段的常量。
static NumberFormat.Field DECIMAL_SEPARATOR
          标识小数点字段的常量。
static NumberFormat.Field EXPONENT
          标识指数字段的常量。
static NumberFormat.Field EXPONENT_SIGN
          标识指数符号 (exponent sign) 字段的常量。
static NumberFormat.Field EXPONENT_SYMBOL
          标识指数符号 (exponent symbol) 字段的常量。
static NumberFormat.Field FRACTION
          标识小数字段的常量。
static NumberFormat.Field GROUPING_SEPARATOR
          标识组分隔符字段的常量。
static NumberFormat.Field INTEGER
          标识整数字段的常量。
static NumberFormat.Field PERCENT
          标识百分数字段的常量。
static NumberFormat.Field PERMILLE
          标识千分数字段的常量。
static NumberFormat.Field SIGN
          标识符号字段的常量。

例子:

public static void main(String[] args) {
        NumberFormat numberFormat = NumberFormat.getInstance();
        StringBuffer stringBuffer1 = new StringBuffer();
        FieldPosition fieldPosition = new FieldPosition(NumberFormat.Field.INTEGER);
        BigDecimal bigDecimal = new BigDecimal("1.23456789");
        stringBuffer1 = numberFormat.format(bigDecimal, stringBuffer1, fieldPosition);
        System.out.println("stringBuffer1 = " + stringBuffer1);
        System.out.println("INTEGER:beginIndex=" + fieldPosition.getBeginIndex() + ",endIndex=" + fieldPosition.getEndIndex());

        fieldPosition = new FieldPosition(NumberFormat.Field.FRACTION);
        StringBuffer stringBuffer2 = new StringBuffer();
        stringBuffer2 = numberFormat.format(bigDecimal, stringBuffer2, fieldPosition);
        System.out.println("stringBuffer2 = " + stringBuffer2);
        System.out.println("FRACTION:beginIndex=" + fieldPosition.getBeginIndex() + ",endIndex=" + fieldPosition.getEndIndex());
    }
stringBuffer1 = 1.235
INTEGER:beginIndex=0,endIndex=1
stringBuffer2 = 1.235
FRACTION:beginIndex=2,endIndex=5
public static void main(String[] args) {
        DateFormat dateFormat = DateFormat.getDateTimeInstance(DateFormat.LONG, DateFormat.LONG);
        StringBuffer stringBuffer = new StringBuffer();
        FieldPosition pos = new FieldPosition(DateFormat.Field.DAY_OF_MONTH);
        stringBuffer = dateFormat.format(new Date(), stringBuffer, pos);
        System.out.println("stringBuffer = " + stringBuffer);
        System.out.println("DATE_FIELD:beginIndex= " + pos.getBeginIndex() + ",endIndex=" + pos.getEndIndex());
    }
stringBuffer = 2016年6月28日 上午11时07分18秒
DATE_FIELD:beginIndex= 7,endIndex=9

java.text.ParsePosition

ParsePosition是Format及其子类所使用的简单类,用来在解析过程中跟踪当前位置。各种Format类中的parseObject方法要求将 ParsePosition对象作为一个变量。解析具有不同格式的字符串时,可以使用同一个ParsePosition,因为索引参数记录的是当前位置。ParsePosition也会记录解析错误的位置。

构造方法

public ParsePosition(int index)

创建一个具有给定初始索引的新 ParsePosition。

例子:

public static void main(String[] args) {
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd");
        String strings[] = {"xxx 2016-06-28 xxx1", "20160628 xxx2"};
        for (int i = 0; i < strings.length; i++) {
            ParsePosition parsePosition = new ParsePosition(4);//从第四位开始处理
            Date date = simpleDateFormat.parse(strings[i], parsePosition);
            //解析错误,返回null
            if (date == null) {
                System.out.println("无效日期:" + strings[i]);
                System.out.println("解析出错的索引=" + parsePosition.getErrorIndex());
                System.out.println("当前索引=" + parsePosition.getIndex());
                continue;
            }
            String substring = strings[i].substring(parsePosition.getIndex());
            System.out.println("日期=" + date + ",剩余部分:" + substring);
        }
    }
日期=Tue Jun 28 00:00:00 CST 2016,剩余部分: xxx1
无效日期:20160628 xxx2
解析出错的索引=8
当前索引=4

java.text.NumberFormat

NumberFormat 是所有数值格式的抽象基类。此类提供格式化和解析数值的接口。NumberFormat 还提供了一些方法来确定哪些语言环境具有数值格式,以及它们的名称是什么。 
NumberFormat 可用于格式化和解析任何语言环境的数值。使代码能够完全独立于小数点、千位分隔符甚至所用特定小数位数的语言环境约定,并与数值格式是否为偶小数无关。

如何获得一个实例?

NumberFormat总共有三种实例,常规数值、货币数值,百分比数值,每种都可以用默认语言环境和指定语言环境。

常规数值:getInstance()(同getNumberInstance())、getInstance(Locale inLocale)(同getNumberInstance(Locale inLocale))

货币数值:getCurrencyInstance()、getCurrencyInstance(Locale inLocale)

百分比数值:getPercentInstance()、getPercentInstance(Locale inLocale)

public static Locale[] getAvailableLocales()

返回一个当前所支持的语言环境数组

void setCurrency(Currency currency) 
设置格式化货币值时此数值格式使用的货币。

void setGroupingUsed(boolean newValue) 
设置此格式中是否使用分组,即是否有千位分隔符(逗号)。

void setMaximumFractionDigits(int newValue) 
设置数的小数部分所允许的最大位数。与解析无关。

void setMaximumIntegerDigits(int newValue) 
设置数的整数部分所允许的最大位数。与解析无关。

void setMinimumFractionDigits(int newValue) 
设置数的小数部分所允许的最小位数。与解析无关。

void setMinimumIntegerDigits(int newValue) 
设置数的整数部分所允许的最小位数。与解析无关。

void setParseIntegerOnly(boolean value) 
设置数是否应该仅作为整数进行解析。与格式化无关。

例子:

public static void main(String[] args) throws Exception {
        //常规数值
        NumberFormat format1 = NumberFormat.getNumberInstance();
        System.out.println(format1.getMaximumIntegerDigits());//2147483647
        System.out.println(format1.getMinimumIntegerDigits());//1
        System.out.println(format1.getMaximumFractionDigits());//3
        System.out.println(format1.getMinimumFractionDigits());//0
        System.out.println(format1.isGroupingUsed());//true
        System.out.println(format1.isParseIntegerOnly());//false

        System.out.println(format1.format(10000000));//10,000,000 默认分组
        System.out.println(format1.format(10000000.000));//10,000,000 小数点后全身0,被舍弃
        System.out.println(format1.format(10000000.001));//10,000,000.001
        System.out.println(format1.format(10000000.0001));//10,000,000 默认最大小数位数是3位

        System.out.println(format1.parse("10000000.001"));//1.0000000001E7 默认可以解析小数
        format1.setParseIntegerOnly(true);
        System.out.println(format1.parse("10000000.001"));//10000000

        //百分比数值
        NumberFormat format2 = NumberFormat.getPercentInstance();
        System.out.println(format2.getMaximumIntegerDigits());//2147483647
        System.out.println(format2.getMinimumIntegerDigits());//1
        System.out.println(format2.getMaximumFractionDigits());//0
        System.out.println(format2.getMinimumFractionDigits());//0
        System.out.println(format2.isGroupingUsed());//true
        System.out.println(format2.isParseIntegerOnly());//false

        System.out.println(format2.format(1.01));//101%
        System.out.println(format2.format(1.001));//100% 默认最大小数位数是0
        format2.setMaximumFractionDigits(1);
        System.out.println(format2.format(1.001));//100.1%

        System.out.println(format2.parse("100.1%"));// 1.001 默认可以解析小数

        //货币格式
        NumberFormat format3 = NumberFormat.getCurrencyInstance();
        System.out.println(format3.getMaximumIntegerDigits());//2147483647
        System.out.println(format3.getMinimumIntegerDigits());//1
        System.out.println(format3.getMaximumFractionDigits());//2
        System.out.println(format3.getMinimumFractionDigits());//2
        System.out.println(format3.isGroupingUsed());//true
        System.out.println(format3.isParseIntegerOnly());//false

        System.out.println(format3.format(10000));//¥10,000.00 默认语言环境是zh_CN

        System.out.println(format3.parse("¥10,000.00"));//10000
    }

java.text.DecimalFormat

DecimalFormat是NumberFormat的一个具体子类,用于格式化十进制数字。该类设计有各种功能,使其能够解析和格式化任意语言环境中的数,包括对西方语言、阿拉伯语和印度语数字的支持。通常不直接调用DecimalFormat的构造方法,要获取具体语言环境的DecimalFormat(包括默认语言环境),可调用NumberFormat的某个工厂方法,如getInstance()。如果看源码会发现getInstance()其实返回的就是DecimalFormat实例,因为以后的版本NumberFormat的工厂方法可能返回不同于DecimalFormat的子类:

 NumberFormat f = NumberFormat.getInstance(loc);
 if (f instanceof DecimalFormat) {
     ((DecimalFormat) f).setDecimalSeparatorAlwaysShown(true);
 }

DecimalFormat包含一个模式和一组符号。可直接使用applyPattern()或间接使用API方法来设置模式。符号存储在DecimalFormatSymbols象中。如果想要改变符号,比如小数点,可以使用和DecimalFormate关联的DecimalFormatSymbols,此类表示了DecimalFormat格式化数字所需的符号集(如小数点、组分隔符等等)。DecimalFormat 根据其语言环境数据为其自身创建一个DecimalFormatSymbols实例。如果需要更改这些符号,可从DecimalFormat#getDecimalFormatSymbols()获得DecimalFormatSymbols对象并修改它。通常程序员不需要修改DecimalFormatSymbols。

特殊符号

0 数字。阿拉伯数字,如果当前位置不存在数字,则显示为0
# 数字。阿拉伯数字,在不影响数值的情况下,当前位置如果为0或者不存在,则不显示
. 数字。小数分隔符或货币小数分隔符
- 数字。减号
, 数字。分组分隔符
E 数字。分隔科学计数法中的尾数和指数。在前缀或后缀中无需加引号
; 子模式边界。分隔正数和负数子模式
% 前缀或后缀。乘以 100 并显示为百分数
\u2030 前缀或后缀。乘以 1000 并显示为千分数
¤(\u00A4) 前缀或后缀。货币记号,由货币符号替换。如果两个同时出现,则用国际货币符号替换。如果出现在某个模式中,则使用货币小数分隔符,而不使用小数分隔符
前缀或后缀。用于在前缀或或后缀中为特殊字符加引号,例如 "‘#‘#" 将 123 格式化为 "#123"。要创建单引号本身,请连续使用两个单引号:"# o‘‘clock"

语法

1、前缀和后缀:数字前后的符号,除 \uFFFE、\uFFFF 和特殊字符以外的所有 Unicode 字符。

2、小数分隔符和千位分隔符应该是不同的字符,否则将不可能进行解析。

3、如果使用具有多个分组字符的模式,则最后一个分隔符和整数结尾之间的间隔才是使用的分组大小。所以 "#,##,###,####" == "######,####" == "##,####,####"。

构造方法

DecimalFormat() 
使用默认模式和默认语言环境的符号创建一个DecimalFormat。 
DecimalFormat(String pattern) 
使用给定的模式和默认语言环境的符号创建一个DecimalFormat。 
DecimalFormat(String pattern, DecimalFormatSymbols symbols) 
使用给定的模式和符号创建一个DecimalFormat。

例子:

public static void main(String[] args) throws Exception {
        DecimalFormatSymbols unusualSymbols = new DecimalFormatSymbols();
        unusualSymbols.setDecimalSeparator(‘|‘);
        unusualSymbols.setGroupingSeparator(‘^‘);

        String strange = "#,##0.###";
        DecimalFormat weirdFormatter = new DecimalFormat(strange, unusualSymbols);
        weirdFormatter.setGroupingSize(4);

        String bizarre = weirdFormatter.format(12345.678);
        System.out.println(bizarre);//1^2345|678
    }
时间: 2024-12-28 19:58:45

java.text.Format及相关类详解的相关文章

Java提高学习之Object类详解(1)

转自:http://www.importnew.com/10304.html 问:什么是Object类? 答:Object类存储在java.lang包中,是所有java类(Object类除外)的终极父类.当然,数组也继承了Object类.然而,接口是不继承Object类的,原因在这里指出:Section 9.6.3.4 of the Java Language Specification:“Object类不作为接口的父类”.Object类中声明了以下函数,我会在下文中作详细说明. 1 prote

Java多线程Callable和Future类详解

     public interface Callable<V>    返回结果并且可能抛出异常的任务.实现者定义了一个不带任何参数的叫做 call 的方法      public interface Future<V>      Future 表示异步计算的结果.计算完成后只能使用 get 方法来获取结果 1.线程处理返回结果 一般开发中,使用多线程,最常见的就是:1.实现Runnable接口:2.继承Thread类. 但是run方法是没有返回结果,很难满足我们的需求.这时,常

Java String类详解

Java字符串类(java.lang.String)是Java中使用最多的类,也是最为特殊的一个类,很多时候,我们对它既熟悉又陌生. 类结构: public final class String extends Object implements Serializable, Comparable<String>, CharSequence 类概述: Java程序中的所有字面值(string literals),即双引号括起的字符串,如"abc",都是作为String类的实例

Java内存模型相关原则详解

在<Java内存模型(JMM)详解>一文中我们已经讲到了Java内存模型的基本结构以及相关操作和规则.而Java内存模型又是围绕着在并发过程中如何处理原子性.可见性以及有序性这三个特征来构建的.本篇文章就带大家了解一下相关概念.原则等内容. 原子性 原子性即一个操作或一系列是不可中断的.即使是在多个线程的情况下,操作一旦开始,就不会被其他线程干扰. 比如,对于一个静态变量int x两条线程同时对其赋值,线程A赋值为1,而线程B赋值为2,不管线程如何运行,最终x的值要么是1,要么是2,线程A和线

QAction类详解:

先贴一段描述:Qt文档原文: Detailed Description The QAction class provides an abstract user interface action that can be inserted into widgets. In applications many common commands can be invoked via menus, toolbar buttons, and keyboard shortcuts. Since the user

Linux下FFMPEG--H264--编码&&解码的C实现与相关原理详解

FFMPEG是很强大的一套视频音频处理库,不过,强大的功能一般免不了复杂的实现,或者更加现实地说,"麻烦"的部署和使用流程 关于"FFMPEG怎么部署"这事就放在另一篇文章啦,下面入正题.. 编码encoder模块和解码decoder模块都有init初始化方法和资源free方法 init初始化方法主要是进行ffmpeg所必需的编解码器的初始化和部分功能方法的参数配置,而free资源释放方法则是相应地进行必要的回收 Encoder模块的实现和细节分析 #include

URLConnection类详解

为了防止无良网站的爬虫抓取文章,特此标识,转载请注明文章出处.LaplaceDemon/SJQ. http://www.cnblogs.com/shijiaqi1066/p/3753224.html URLConnection概述 URLConnection是一个抽象类,表示指向URL指定资源的活动连接. URLConnection类本身依赖于Socket类实现网络连接.一般认为,URLConnection类提供了比Socket类更易于使用.更高级的网络连接抽象.但实际上,大多数程序员都会忽略它

Android开发之Html类详解

在进行Android开发中经常回忽略Html类.这个类其实很简单,就是将HTML标签文本解析成普通的样式文本.下面就让我么看一下这个类的具体介绍. 类结构: java.lang.Object    ? android.text.Html 类概述: 这个类用于处理的HTML字符串并将其转换成可显示的样式文本.但并不是所有的HTML标记的支持. 公有方法: 说其简单是应为它就有四个方法: Public Methods static String escapeHtml(CharSequence tex

Java学习-007-Log4J 日志记录配置文件详解及实例源代码

此文主要讲述在初学 Java 时,常用的 Log4J 日志记录配置文件详解及实例源代码整理.希望能对初学 Java 编程的亲们有所帮助.若有不足之处,敬请大神指正,不胜感激!源代码测试通过日期为:2015-1-30 13:54:02,请知悉. 所需的 jar 包下载链接为:http://yunpan.cn/cKE56sxqtQCfP  访问密码 63d8 有关 Log4J 日志文件中日志级别及文件配置的详细情况,在 Log4J 的配置文件(xml.properties)中有详细的介绍,敬请参阅!