天天看點

JAVA中的format

1.    java.text.Format 2

1.1.     Format的方法... 2

1.2.     Format的子類... 2

1.3.     DateFormat的用法... 2

1.4.     MessageFormat的用法... 2

1.5.     NumberFormat的用法... 3

1.5.1.      NumberFormat的介紹... 3

1.5.2.      子類DecimalFormat 3

1.5.3.      子類ChoiceFormat 3

1.5.4.      ChoiceFormat的例子... 3

1.5.5.      ChoiceFormat的pattern構造方法... 4

1.5.6.      其它的數字格式化... 4

2.    java.util.Formatter. 5

2.1.     介紹... 5

2.2.     轉換(conversion) 5

2.2.1.      正常... 5

2.2.2.      字元... 6

2.2.3.      整數... 6

2.2.4.      浮點... 6

2.2.5.      日期/時間... 6

2.2.6.      百分比... 6

2.2.7.      行分隔符... 6

2.3.     标志(flags) 6

2.4.     寬度(width) 6

2.5.     精度(.precision) 6

3.    java.util.regex.Pattern. 7

3.1.     介紹... 7

3.2.     關于regex. 7

3.3.     Matcher(比對器) 7

在Java中,有java.text.Format,java.util.Formatter,java.util.regex.Pattern三個格式化相關的體系,使用起來較為複雜,在這裡總結一下。

1.        java.text.Format

1.1.       Format的方法

java.text.Format做為一個抽象類,有二個抽象方法,

format(Object obj, StringBuffer toAppendTo,FieldPosition pos):格式化一個對象,并将得到的文本追加到給定的字元緩沖區。是将obj格式化為字元串,并加入到toAppendTo中。

parseObject(String source, ParsePosition pos): 分析字元串文本,生成一個對象。是format方法的逆向方法,将String轉化為Object。

另外的format和parseObject這兩個方法的重載。

方法formatToCharacterIterator(Objectobj)并非抽象方法,api上要求子類必須實作這個方法。

1.2.       Format的子類

Java 2 平台為格式化日期、消息和數字分别提供了三個特殊的 Format 的子類:DateFormat(抽象類)、MessageFormat和 NumberFormat(抽象類)。

           ——>DateFormat   ——>SimpleDateFormat

Format  ——>MessageFormat

              ——>NumberFormat——>ChoiceFormat

                                          ——> DecimalFormat用于格式化十進制數字

1.3.       DateFormat的用法

DateFormat 是日期/時間格式化子類的抽象類, 有一些static的get***Instance()方法來獲得執行個體。通過設定結果的長度和地區,來獲得日期,時間等的格式formatter。不太常用。

一般會使用SimpleDateFormat子類,newSimpleDateFormat("yyyy-MM-dd")或newSimpleDateFormat("yyyy-MM-dd HH:mm:ss"),來獲得常用的時間格式。DateFormat 的get***Instance()方法一般也是獲得SimpleDateFormat。

看DateFormat的源代碼有個疑問,如果繼承了DateFormat類,那DateFormat. get***Instance()的方法還是傳回SimpleDateFormat? DateFormat.get是私有的,也不能覆寫。

DateFormat類中還有一些static的字段,如WEEK_OF_MONTH_FIELD,WEEK_OF_YEAR_FIELD。api上說在FieldPosition中使用,用于對齊。

java.util.Calendar也是日期操作相關的類,實作類為GregorianCalendar。主要對日期進行操作。注意add方法和roll方法的差別,roll方法不更改更大的字段。還有一些靜态的變量DAY_OF_MONTH,DAY_OF_WEEK等,在

get

/

set/

add/roll方法中使用。

1.4.       MessageFormat的用法

和SimpleDateFormat一樣,也需要傳入一個pattern。如

String result = MessageFormat.format(

    "At {1,time} on {1,date}, there was {2} on planet{0,number,integer}.",

     7,new Date(), “ a message ”);

其中

{1,time}中1是指第幾個參數,time是指格式化的類型。根據api進行設定,是調用NumberFormat和DateFormat進行格式化的。

還可以調用parse方法将字元串轉化為Obejct。

1.5.       NumberFormat的用法

1.5.1.NumberFormat的介紹

NumberFormat 是所有數字格式的抽象基類。類結構與DateFormat類似。主要也是通過get***Instance方法獲得實作類DecimalFormat。

比較常用的方法有:

setParseIntegerOnly:隻影響分析。設為true,則忽略小數點以後的位置。

setDecimalSeparatorAlwaysShown:隻影響格式化,且隻影響小數點後沒有數字的情況?設定分組符号是否顯示。例如1,234中的,号是否顯示。

setGroupingUsed

:是否分組。如果此格式中使用了組,則傳回 true。例如,在英國語言環境中,如果設定了組,則數 1234567 可能被格式化為 "1,234,567"。

還可以設定小數/整數部分的最大/小位數。

關于parse方法中的ParsePosition和 format方法中的FieldPosition待研究。

1.5.2. 

子類DecimalFormat

DecimalFormat 是NumberFormat 的一個具體子類,用于格式化十進制數字。在DecimalFormat中傳入pattern,可以自定義格式化類型。舍入方式是half-even(四舍五入)。

DecimalFormat 模式包含正數和負數子模式,例如 "#,##0.00;-#,##0.00"。;後面的代表負數模式。單獨的 "0.00"等效于 "0.00;-0.00"。如果存在顯式的負數子模式,則它僅指定負數字首和字尾;

0:代表是數字;如果不存在則顯示為0;

#:代表是數字;

,:分組分隔符;沒有則不分組

1.5.3. 子類ChoiceFormat

ChoiceFormat通常用于在MessageFormat 中處理複數。建立 ChoiceFormat 時,可以指定一個 format 數組和一個limit 數組。這些數組的長度必須相同。

如api中用于轉換星期的例子

 double[] limits = {1,2,3,4,5,6,7};

 String[] monthNames ={"Sun","Mon","Tue","Wed","Thur","Fri","Sat"};

 ChoiceFormat form = new ChoiceFormat(limits,monthNames);

 ParsePosition status = new ParsePosition(0);

 for (double i = 0.0; i <= 8.0; ++i) {

     status.setIndex(0);

     System.out.println(i + " -> "+ form.format(i) + " -> "

                              +form.parse(form.format(i),status));

 }

form.format(i)根據limits的數字轉換為星期幾的名稱。limits中的數字必須按升序排列,如果提供的數字不在limits中,則選擇使用第一個或最後一個索引。

form.parse(form.format(i),status),則根據Name轉換為limits中的值。

1.5.4. ChoiceFormat的例子

下面是ChoiceFormat的api中一個較複雜的帶模式格式的例子, 和MessageFormat一起使用:

 //生成ChoiceFormat

 double[] filelimits = {0,1,2};

 String[] filepart = {"are nofiles","is one file","are {2} files"};//這裡的2是指從testArgs中取第二個元素的值

 ChoiceFormat fileform = newChoiceFormat(filelimits, filepart);

//定義Format數組testFormats,分别為ChoiceFormat,null,NumberFormat

//ChoiceFormat用于{0}, null用于{1},NumberFormat用于{2}

 Format[] testFormats = {fileform, null,NumberFormat.getInstance()};

//将MessageFormat的formats設為testFormats

//testFormats中的格式順序對應于模式字元串中的格式元素的順序

//最好使用setFormatsByArgumentIndex方法,而不是使用setFormats

 MessageFormat pattform = newMessageFormat("There {0} on {1}");

 pattform.setFormats(testFormats);

//進行fomat

 Object[] testArgs = {null, "ADisk",null};

 for (int i = 0; i < 4; ++i) {

     testArgs[0] = new Integer(i);

     testArgs[2] = testArgs[0];

//此時的testArgs值為{0, "ADisk",0}

//根據MessageFormat的定義,對testArgr元素進行處理

    System.out.println(pattform.format(testArgs));

 }

1.5.5. ChoiceFormat的pattern構造方法

ChoiceFormat還有另外一個構造方法,傳入pattern。

為ChoiceFormat 對象指定一個模式是相當直接的。例如:

ChoiceFormat fmt= new ChoiceFormat(

      "-1#is negative| 0#is zero orfraction | 1#is one |1.0<is 1+ |2#is two |2<is more than 2.");

其中數字#是按照大小順序排列的, formate方法中傳入參數x,如果x在0,1之間,則按照0處理。

1.5.6. 其它的數字格式化

另外在對數字進行格式化時,也可以考慮使用java.math.BigDecimal。

如setScale(int newScale,int roundingMode):newScale指精确度,即保留幾位小數。roundingMode指舍入模式,常用的是四舍五入。DecimalFormat貌似隻能使用四舍五入,如果使用别的舍入方式,就要使用BigDecimal了。

java.lang.Integer中的幾個轉換進制的方法也比較實用

toBinaryString(int i): 以二進制(基數 2)無符号整數形式傳回一個整數參數的字元串表示形式。

toHexString(int i): 以十六進制的無符号整數形式傳回一個整數參數的字元串表示形式

toOctalString(int i) :以八進制(基數 8)無符号整數形式傳回一個整數參數的字元串表示形式。

2.        java.util.Formatter

2.1.       介紹

Formatter類是個final的class,printf 風格的格式字元串的解釋程式,和java.text.Format中的功能有很多重複的地方。

Formatter比較常見的使用方法是String.format(format,args),System.out.printf(format,args)等。這裡隻是簡單總結一下,詳細的參照api。下面的每節是對格式說明符中的元素的說明。

正常類型、字元類型和數值類型的格式說明符的文法如下:

%[argument_index$][flags][width][.precision]conversion

其中%和conversion(轉換類型)是必須的,

%表示正規表達式的開始。

可選的argument_index$,指的是參數在參數清單中的位置。如果設定argument_index$,則按照args的順序依次處理。

可選的 flags(标志) 是修改輸出格式的字元集。有效标志的集合取決于轉換類型。

可選 width(寬度) 是一個非負十進制整數,表明要向輸出中寫入的最少字元數。

可選 precision(精度) 是一個非負十進制整數,通常用來限制字元數。特定行為取決于轉換類型。

2.2.       轉換(conversion)

轉換是核心,按參數類别可以分為正常,字元,整數,浮點,日期/時間,百分比,行分隔符。不區分大小寫。

2.2.1. 正常

正常的傳回值為字元串,有:

b:結果為“true/false”。參數 arg 為 null或boolean/Boolean型的false時,傳回字元串的“false”。否則傳回字元串的“true”。

h:結果為十六進制的字元串。如果參數 arg 為 null,則結果為 "null"。否則,結果為調用Integer.toHexString(arg.hashCode()) 得到的結果。

s:比較常用的轉換,取得字元串。如果參數 arg 為 null,則結果為 "null"。如果 arg 實作 Formattable,則調用 arg.formatTo。否則,結果為調用 arg.toString() 得到的結果。

2.2.2.字元

c: 結果是一個 Unicode 字元

2.2.3.整數

是對進制的操作,有:

d:結果被格式化為十進制整數

o:結果被格式化為八進制整數

x:結果被格式化為十六進制整數

2.2.4.浮點

e:結果被格式化為用計算機科學記數法表示的十進制數

f :結果被格式化為十進制數

g:根據精度和舍入運算後的值,使用計算機科學記數形式或十進制格式對結果進行格式化

a:浮點  結果被格式化為帶有效位數和指數的十六進制浮點數

2.2.5.日期/時間

t:日期和時間轉換字元的字首。對于日期/時間的轉換,以t開頭再指定轉換内容。

如Calendar c = newGregorianCalendar(1995, MAY, 23);

   String s =String.format("Duke's Birthday: %1$tm %1$te,%1$tY", c);

具體參數的意義參照api。

2.2.6.百分比

%:結果為字面值 '%'。

2.2.7.行分隔符

n:生成一個換行符。為平台相關。

2.3.       标志(flags)

标志有'-','#','+','  ','0',',','('。常用的是'-':将結果設為左對齊。同時flag的使用依賴于conversion。

2.4.       寬度(width)

寬度是将向輸出中寫入的最少字元數。對于行分隔符轉換,不适用寬度,如果提供寬度,則會抛出異常。

2.5.       精度(.precision)

對于正常參數類型,精度是将向輸出中寫入的最多字元數。

對于浮點轉換 'e'、'E' 和 'f',精度是小數點分隔符後的位數。

如果轉換是 'g' 或 'G',那麼精度是舍入計算後所得數值的所有位數。如果轉換是 'a' 或 'A',則不必指定精度。

精度的優先級大于寬度。

3.        java.util.regex.Pattern

3.1.       介紹

Pattern(模式)是正規表達式的編譯表示形式,經常和java.util.regex.Matcher。Pattern沒有提供構造函數。通過調用Pattern. compile (String regex)方法來獲得執行個體。pattern.matcher (CharSequence input);來判斷是否input是否可以與regex比對。compile

通過Matcher m = p.matcher("aaaaab");方法來獲得Matcher。

pattern.split(CharSequence input);可以将input分隔成一個String數組。

3.2.       關于regex

字元類比較常用, []是對字元的羅列。如[abc]。[a-z&&[^bc]]    的解釋為a 到 z,除了 b 和 c:[ad-z](減去)。

還有字元,預定義字元類,邊界比對器也比較常用。具體參照api。

Greedy 數量詞也需要了解。

X? 表示X,一次或一次也沒有

X* 表示X,零次或多次

X+ 表示X,一次或多次

X{n} 表示X,恰好 n 次  

X{n,} 表示 X,至少 n 次

X{n,m} 表示X,至少 n 次,但是不超過 m 次。

Greedy 數量詞,這種比對原則就叫作"貪婪" 模式。總是盡可能多的比對符合它規則的字元。

Reluctant 數量詞,Possessive 數量詞不曉得有啥差別。

組和捕獲:捕獲組可以通過從左到右計算其開括号來編号。如(ca)(t)。

3.3.       Matcher(比對器)

通過調用模式的 matcher 方法從模式建立比對器。建立比對器後,可以使用它執行三種不同的比對操作:

matches 方法嘗試将整個輸入序列與該模式比對。 注意是整個輸入字元串。

lookingAt 嘗試将輸入序列從頭開始與該模式比對。

find 方法掃描輸入序列以查找與該模式比對的下一個子序列。

方法:

matcher.appendReplacement(StringBuffersb, String replacement):實作非終端追加和替換步驟。就是将模式比對到的字元串,替換為replacement,并将區域加入到sb中。區域的操作,參看match.region,match. regionStart, match.regionEnd。

matcher.appendTail(StringBuffersb) 實作終端追加和替換步驟。可以在一次或多次調用appendReplacement 方法後調用它來複制剩餘的輸入序列。Tail的意思尾部,也就是剩餘的意思。這裡的終端應該就是指尾部。

matcher.replaceAll(Stringreplacement):替換模式與給定替換字元串相比對的輸入序列的每個子序列。比較友善的方法,用replacement直接替換掉與模式比對的字元串。

與模式中的組和捕獲相關的方法,有match.group,match.groupCount。如模式(ca)(t)的groupCount就是2。