DecimalFormat pattern problem
I try to format a number using NumberFormatter in Android. I use the code bellow and it works perfectly:
NumberFormat formatter = new DecimalFormat("###,###");
String myFormattedString = formatter.format(123456);
But, when i use a pattern with space, like that: new DecimalFormat("###,# ##");
it throws an IllegalArgumentException
. I've read documentation about NumberFormatter and DecimalFormatter and found nothing about spaces in patterns. Can anyone explane me why can't i use spaces or how to add them as al开发者_JAVA百科lowed characters.
Thanks in advance!!!
You can not put spaces in the middle of a number: it is not a valid format.
If you look at the JavaDoc of DecimalFormat
, you'll see this:
Prefix: any Unicode characters except \uFFFE, \uFFFF, and special characters Suffix: any Unicode characters except \uFFFE, \uFFFF, and special characters Number: Integer Exponentopt Integer . Fraction Exponentopt
Without copying the entire doc, none of the components of the Number
pattern accept spaces, so trying to fit a space in the middle will not work. You can only use spaces in the prefix or suffix.
In a regular JDK this does not throw an exception - it just formats the number as 123,456
.
It is not clear what is the space in your example. You have a couple of options for a symbol's role:
- decimal separator
- group separator
- exponent separator
- monetary decimal separator
You can set each of these with:
DecimalFormatSymbols symbols = formatter.getDecimalFormatSymbols();
symbols.setGroupingSeparator(' ');
formatter.setSymbols(symbols);
I've achieved my goal by making my own formatter using standart formatter and finding prohibited symbols using exeptions. Hope it will be useful for someone else.
public static String getFormattedNumberWithPattern(String aPattern,
float aNumber) {
String lFormattedNumber = null;
String lOriginalPattern = aPattern;
try {
Hashtable<Integer, String> lIlligalChars = new Hashtable<Integer, String>();
// analyze illegal characters
for (int i = aPattern.length() - 1; i >= 0; i--) {
char[] lAux = new char[1];
aPattern.getChars(i, i + 1, lAux, 0);
try {
// if character is illegal, it throws an exception
@SuppressWarnings("unused")
NumberFormat lNumberFormatter = new DecimalFormat("#"
+ lAux[0] + "#");
} catch (IllegalArgumentException e) {
// add illegal chars and indexes to dictionary
lIlligalChars.put(new Integer(i), String.valueOf(lAux[0]));}}
Enumeration<String> lChars = lIlligalChars.elements();
while (lChars.hasMoreElements()) {
String lIllegalChar = lChars.nextElement();
// remove illegal chars from pattern
aPattern = removeChar(aPattern, lIllegalChar.charAt(0));
}
// format number using legal pattern
NumberFormat lNumberFormatter = new DecimalFormat(aPattern);
lFormattedNumber = lNumberFormatter.format(aNumber);
int lLenghtDifference = lOriginalPattern.length()
- lFormattedNumber.length();
// add illegal chars to formatted string using their indexes
Enumeration<Integer> lKeys = lIlligalChars.keys();
while (lKeys.hasMoreElements()) {
Integer lIllegalCharIndex = lKeys.nextElement();
int lInsertIndex = lIllegalCharIndex.intValue()
- lLenghtDifference;
// insert illegal chars into formatted number
if (lInsertIndex >= 0
|| lInsertIndex < lFormattedNumber.length()) {
lFormattedNumber = new StringBuffer(lFormattedNumber)
.insert(lInsertIndex,
lIlligalChars.get(lIllegalCharIndex)
.charAt(0)).toString();
}
}
} catch (Exception e) {
// Log.d("info", "formater error:" + e + "mask: " + aPattern
// + " number:" + aNumber);
}
return lFormattedNumber;
}
public static String removeChar(String s, char c) {
StringBuffer r = new StringBuffer(s.length());
r.setLength(s.length());
int current = 0;
for (int i = 0; i < s.length(); i++) {
char cur = s.charAt(i);
if (cur != c)
r.setCharAt(current++, cur);
}
r.setLength(current);
return r.toString();
}
精彩评论