Reputation: 1083
I'm looking for an efficient way to have number String
s properly formatted so it could be parsed to a double
value.
Requirements:
Double.parseDouble(numberString);
Examples: 1.234.567,89 => 1234567.89; 5 => 5; 6.3 => 6.3; 5.23 => 5.23;...
To check if the String
is a number, I'd like to user either regex or NumberUtils.isNumber(numberString)
. Only problem with the latter one is that it has issues with strings like "123,45".
My current attempt (that feels pretty inefficient):
LOGGER.debug("Normalizing price string: " + price);
String str = price;
if (str.contains(",") || str.contains(".")) {
int pos = -1;
if (str.contains(",")) pos = str.lastIndexOf(',');
else if (str.contains(".")) pos = str.lastIndexOf(".");
//Remove all the dots and commas first
str = str.replaceAll("[,.]", "");
if (!NumberUtils.isNumber(str) || !NumberUtils.isDigits(str)) {
LOGGER.debug("String does not match expected pattern");
throw new NumberFormatException();
} else {
//Add a dot back in
if (str.length() <= 2) {
StringBuilder first = new StringBuilder(str.substring(0, pos));
first.append('.');
String last = str.substring(pos);
str = first + last;
} else {
StringBuilder first = new StringBuilder(str.substring(0, str.length() - 2));
first.append('.');
String last = str.substring(str.length() - 2);
str = first + last;
}
}
}
LOGGER.debug("Normalised result: " + str);
return str;`
How can this formatting be simplified, made more efficient, and correctly handle incorrect input?
Applied solution
String str = price;
DecimalFormatSymbols dfsDot = new DecimalFormatSymbols();
dfsDot.setDecimalSeparator('.');
DecimalFormatSymbols dfsComma = new DecimalFormatSymbols();
dfsComma.setDecimalSeparator(',');
DecimalFormat dfDot = new DecimalFormat("#,##0.00", dfsDot);
DecimalFormat dfComma = new DecimalFormat("#,##0.00", dfsComma);
double d = 0;
try {
if (!str.contains(",") && !str.contains(".")) {
return str;
} else if (str.contains(",")) d = (Double) dfComma.parse(str);
else if (str.contains(".")) d = (Double) dfDot.parse(str);
str = "" + d;
} catch (ParseException e) {
LOGGER.debug(str + " couldn't be cast to Double");
e.printStackTrace();
return price;
}
Upvotes: 0
Views: 152
Reputation: 5048
Do you know DecimalFormat
?
DecimalFormatSymbols dfs =new DecimalFormatSymbols();
dfs.setDecimalSeparator('.');
DecimalFormat df = new DecimalFormat("#,##0.00",dfs);
double d = df.parse("123.45").doubleValue();
System.out.println(d);
It prints:
123.45
Upvotes: 3