2011-11-01 76 views
2

您好我想知道如何格式化BigDecimal的代表數字,百分比,款項,在語言環境,並從字符串返回BigDecimal的整數字符串。我使用的DecimalFormat功能強大,但我不確定如何在默認用戶區域設置中使用轉換爲精確類型。我第一次使用這個:如何數值轉換代表如百分比,貨幣字符串,返回的BigDecimal使用的DecimalFormat

DecimalFormat.getCurrencyInstance().format(obj); 
DecimalFormat.getCurrencyInstance().parse(source); 

但是,它有很大數量它的歪曲其價值。所以我找到並得到這個:

DecimalFormat decimalFormat = new DecimalFormat(); 
decimalFormat.setParseBigDecimal(true); 
BigDecimal bd = (BigDecimal) decimalFormat.parse(value); 

但如何結合這些認爲。我可能需要將DecimalFormat設置爲NumberFormat.get ??? instance()中使用的某種模式,但我不知道如何以及是否得不到某些奇怪的行爲。

所以請有經驗的人可以幫我嗎?謝謝帕維爾

回答

1

我認爲你最好的選擇是假設getCurrencyInstace()返回DecimalFormat,它可能在所有「重要」的語言環境中。爲了安全起見,你可以使用instanceof

public static BigDecimal parseCurrencyPrecise (String value) 
{ 
    NumberFormat format = NumberFormat.getCurrencyInstance(); 
    if (format instanceof DecimalFormat) 
     ((DecimalFormat) format).setParseBigDecimal (true); 

    Number result = format.parse (value); 
    if (result instanceof BigDecimal) 
     return (BigDecimal) result; 
    else { 
     // Oh well... 
     return new BigDecimal (result.doubleValue()); 
    } 
} 

在我們的應用中,我們基本上做不同的事情,你會需要SimpleDateFormat,但只有DateFormat在一般的情況下是相同的。

0

過了一會兒寫了這個。它似乎在工作,但我不確定它是否能在所有時代都能正常工作。也許它可以幫助別人。我也希望它不會違反任何許可證)。

import java.math.BigDecimal; 
import java.text.DecimalFormat; 
import java.text.DecimalFormatSymbols; 
import java.text.ParseException; 
import java.util.Currency; 
import java.util.Locale; 

import com.ibm.icu.impl.ICUResourceBundle; 
import com.ibm.icu.text.NumberFormat; 
import com.ibm.icu.util.UResourceBundle; 

public class NumericHelper { 

    public static BigDecimal parseStringToBigDecimal(String value, DecimalFormat decimalFormat) throws ParseException { 
     decimalFormat.setParseBigDecimal(true); 
     return (BigDecimal) decimalFormat.parse(value); 
    } 

    /** 
    * Extracted code from {@link NumberFormat#getPattern()} and 
    * {@link java.text.NumberFormat#getInstance(Locale desiredLocale, int choice)} with some 
    * modifications to get DecimalFormat with good Pattern 
    * 
    * @param choice is static values from class {@link NumberFormat} eg 
    *   {@link NumberFormat#INTEGERSTYLE} 
    */ 
    public static DecimalFormat getDecimalFormatWithPattern(Locale desiredLocale, int choice) { 
     ICUResourceBundle rb = (ICUResourceBundle) UResourceBundle.getBundleInstance(ICUResourceBundle.ICU_BASE_NAME, desiredLocale); 
     String[] numberPatterns = rb.getStringArray("NumberPatterns"); 

     DecimalFormatSymbols symbols = DecimalFormatSymbols.getInstance(desiredLocale); 
     int entry = (choice == NumberFormat.INTEGERSTYLE) ? NumberFormat.NUMBERSTYLE : choice; 
     DecimalFormat format = new DecimalFormat(numberPatterns[entry], symbols); 

     if (choice == NumberFormat.INTEGERSTYLE) { 
      format.setMaximumFractionDigits(0); 
      format.setDecimalSeparatorAlwaysShown(false); 
      format.setParseIntegerOnly(true); 
     } 
     else if (choice == NumberFormat.CURRENCYSTYLE) { 
      adjustForCurrencyDefaultFractionDigits(format); 
     } 

     return format; 
    } 

    /** 
    * Extracted from {@link DecimalFormat#adjustForCurrencyDefaultFractionDigits()} because it can 
    * not be called 
    */ 
    protected static void adjustForCurrencyDefaultFractionDigits(DecimalFormat decimalFormat) { 
     DecimalFormatSymbols symbols = decimalFormat.getDecimalFormatSymbols(); 

     Currency currency = symbols.getCurrency(); 
     if (currency == null) { 
      try { 
       currency = Currency.getInstance(symbols.getInternationalCurrencySymbol()); 
      } 
      catch (IllegalArgumentException e) { 
      } 
     } 
     if (currency != null) { 
      int digits = currency.getDefaultFractionDigits(); 
      if (digits != -1) { 
       int oldMinDigits = decimalFormat.getMinimumFractionDigits(); 
       // Common patterns are "#.##", "#.00", "#". 
       // Try to adjust all of them in a reasonable way. 
       if (oldMinDigits == decimalFormat.getMaximumFractionDigits()) { 
        decimalFormat.setMinimumFractionDigits(digits); 
        decimalFormat.setMaximumFractionDigits(digits); 
       } 
       else { 
        decimalFormat.setMinimumFractionDigits(Math.min(digits, oldMinDigits)); 
        decimalFormat.setMaximumFractionDigits(digits); 
       } 
      } 
     } 
    } 
} 

下一個其他的時間後,我想通NumberFormat.get ***實例()方法它回報它的子類(DecimalFormat的)。我不知道這是如何工作的,但它的工作原理。在代碼中是一瞬間,即試圖從LocaleServiceProviderPool獲取格式,所以我相信它也會返回DecimalFormat,如果是這樣,那沒問題使用這種原始方法並投射到DecimalFormat,但是如果不是,您必須檢查它。在代碼中我寫的是這部分省略

相關問題