JFormattedTextField: the formatted text to numbers without spaces - java

I've got a little problem with JFormattedTextField: I want to hold and retrieve numbers from 1000 to 65535. But when I retriev value (7000) from JFormattedTextField, it have one space like 7 000, and when I parse value to Integer (Integer.parseInt(formattedTextField.getText())), it fail.
java.lang.NumberFormatException: For input string: "7 000"
If I do this with MaskFormatter() and .setMask("#####") it's ok, but I want to do this with NumberFormatter().
How can I setup JFormattedTextField without an additon space?
NumberFormatter nfsoc = new NumberFormatter();
nfsoc.setMaximum(Short.MAX_VALUE*2 - 1);
nfsoc.setMinimum(1);
nfsoc.setAllowsInvalid(false);
formattedTextField = new JFormattedTextField(nfsoc);
formattedTextField.setText("7000");
int socket = Integer.parseInt(formattedTextField.getText())
//java.lang.NumberFormatException: For input string: "7 000"
I expect the output of Integer.parseInt(tfServerSocket.getText()) to be 7000, but the actual output is //java.lang.NumberFormatException: For input string: "7 000"

There are two ways to parse an integer.
NumberFormatter uses a localized NumberFormat, which means it formats and parses according to your locale (country/region).
Integer.parseInt doesn’t care about locale. It always expects numbers in the same format used by Java source code, namely “[±]ddd…” (all ASCII digits, optionally preceded by a sign).
Use the getValue() method of JFormattedTextField. It exists specifically to do what you’re trying to do: obtain the value of the JFormattedTextField.
It also has the advantage that it will allow your code to work in all locales, not just yours. For instance, in the United States, your example value is written 7,000. In Germany, it’s written 7.000.
Number socketValue = (Number) formattedTextField.getValue();
if (socketValue == null) {
JOptionPane.showMessageDialog(
formattedTextField.getTopLevelAncestor(),
"A valid port valid is required.",
"Cannot create connection",
JOptionPane.ERROR_MESSAGE);
return;
}
int socket = socketValue.intValue();

To get rid of addition space:
NumberFormatter nfsoc = new NumberFormatter();
NumberFormat nf = NumberFormat.getIntegerInstance();
nf.setGroupingUsed(false); // It removes any separator
nfsoc.setFormat(nf);
nfsoc.setMaximum(Short.MAX_VALUE*2 - 1);
nfsoc.setMinimum(1);
nfsoc.setAllowsInvalid(false);

I've found out it not a space but special character \p{Zs}
tfServerSocket.getText().replaceAll("\p{Zs}", "") = 7000 // without any addition character!

Related

GWT - formatting numbers in default locale regardless of selected locale

I'm trying to format and parse numbers using GWT's NumberFormat but I would like to use the default format (for ex. that of EN locale) regardless of user selected locale, so users can select any language, but I want the numbers to be displayed and parsed using the default format (for ex. 1,234.89).
Is there a way to do this?
EDIT:
For ex. this code only works in EN locale, in RU I get NumberFormatException
NumberFormat format = NumberFormat.getFormat("#,##0.00");
String n = "1,234.89";
double value = format.parse(n);
//do something with value...
I would need to get a NumberFormat instance for locale EN, but I can't find any method/constructor in the javadocs that can do this.
I you have the number you should use NumberFormat.format, not NumberFormat.parse:
NumberFormat format = NumberFormat.getFormat("#,##0.00");
Double n = 1234.89;
RootPanel.get().add(new HTML("Number: " + format.format(n)));
I you already have a formated String representation of the number, you don't need NumberFormat:
String n = "1,234.89";
RootPanel.get().add(new HTML("Number: " + n));
NumberFormat always parses a localized text. It uses NumberConstants witch are instantiated via deferred binding according to current locale. Unfortunately you can not force using other NumberConstants.
But you know the default grouping separator (,) and decimal separator (.). You can also get the grouping and decimal separator for current locale. So you just need to replace them before parsing.
String n = "1,234.89";
n = n.replace(",", LocaleInfo.getCurrentLocale().getNumberConstants().groupingSeparator());
n = n.replace(".", LocaleInfo.getCurrentLocale().getNumberConstants().decimalSeparator());
double value = format.parse(n);
This should work for any locale.
To format a number with default locale just do the opposite replacements after formatting in current locale.

How to parse number string containing commas into an integer in java?

I'm getting NumberFormatException when I try to parse 265,858 with Integer.parseInt().
Is there any way to parse it into an integer?
Is this comma a decimal separator or are these two numbers? In the first case you must provide Locale to NumberFormat class that uses comma as decimal separator:
NumberFormat.getNumberInstance(Locale.FRANCE).parse("265,858")
This results in 265.858. But using US locale you'll get 265858:
NumberFormat.getNumberInstance(java.util.Locale.US).parse("265,858")
That's because in France they treat comma as decimal separator while in US - as grouping (thousand) separator.
If these are two numbers - String.split() them and parse two separate strings independently.
You can remove the , before parsing it to an int:
int i = Integer.parseInt(myNumberString.replaceAll(",", ""));
If it is one number & you want to remove separators, NumberFormat will return a number to you. Just make sure to use the correct Locale when using the getNumberInstance method.
For instance, some Locales swap the comma and decimal point to what you may be used to.
Then just use the intValue method to return an integer. You'll have to wrap the whole thing in a try/catch block though, to account for Parse Exceptions.
try {
NumberFormat ukFormat = NumberFormat.getNumberInstance(Locale.UK);
ukFormat.parse("265,858").intValue();
} catch(ParseException e) {
//Handle exception
}
One option would be to strip the commas:
"265,858".replaceAll(",","");
The first thing which clicks to me, assuming this is a single number, is...
String number = "265,858";
number.replaceAll(",","");
Integer num = Integer.parseInt(number);
Or you could use NumberFormat.parse, setting it to be integer only.
http://docs.oracle.com/javase/1.4.2/docs/api/java/text/NumberFormat.html#parse(java.lang.String)
Try this:
String x = "265,858 ";
x = x.split(",")[0];
System.out.println(Integer.parseInt(x));
EDIT :
if you want it rounded to the nearest Integer :
String x = "265,858 ";
x = x.replaceAll(",",".");
System.out.println(Math.round(Double.parseDouble(x)));

Convert input of BigDecimal locale dependent?

I'm trying save a values' input field to a BigDecimal. Which already works.
But it produces strange results if I enter decimal deliminator that is not of the locale type.
eg:
class Payment {
BigDecimal amount;
}
<p:inputText id="amount" value="#{payment.amount}">
<f:convertNumber locale="en"/>
</p:inputText>
<h:outputText value="#{payment.amount}" />
If I input 10,10
I get: 1,010.00
So the value is taken as 1010
How could I work around this? What am I doing wrong here?
ty
The commas are not significant when parsing an English-locale number. Java's raw Number types will not retain any formatting information - that's just presentation data.
The logic for the inputText with a NumberConverter goes like this:
NumberFormat formatter = NumberFormat.getNumberInstance(Locale.ENGLISH);
// NumberConverter turns input string into Number
Number number = formatter.parse("10,10");
// Expression language coerces the Number to BigDecimal
BigDecimal decimal = BigDecimal.valueOf(number.doubleValue());
// On output back to browser:
String output = formatter.format(decimal);
System.out.println(output);
The outputText doesn't have a converter, so will merely call toString() on its value binding (the BigDecimal.)
I would expect the results to be 1,010 and 1010.0 respectively.
The behavior of NumberConverter is documented in the javadoc. The rules for EL type coercion are documented in JSR 245:
Coerce A to Number type N
If A is Number, coerce quietly to type N using the following algorithm:
If N is BigDecimal,
If A is a BigInteger, return new BigDecimal(A)
Otherwise, return new BigDecimal(A.doubleValue())
If you want to use the user's browser locale to interpret number formats, remove the locale attribute. If you want a converter to treat both periods and commas as decimal separators, provide your own Converter implementation.
As McDowel clearly stated in the comments - EN locale states that , is a delimiter for thousands and . is a delimiter for decimal point.. if you like to use "," as decimal separator, use a locale that has given format (for example french (fr))
In java i would suggest following:
// Using french locale as it is in form of "123 456 789,012345"
DecimalFormat df = (DecimalFormat)
NumberFormat.getInstance(Locale.FRENCH);
df.setParseBigDecimal(true);
// Replace all dots (due to the french format) so we handle "." as well as ","
hodnota = hodnota.replace('.', ',');
try {
return (BigDecimal) df.parseObject(hodnota);
} catch(ParseException e) {
// TODO: What ever you desire
}

How to get this number format in java?

Lets say I am having a number as follows :
long number = 32301672060;
I want the following the format for the number :
323.016.720,60
i.e the last two digits should be separated by comma and then dot between every three digits.
Suppose the another number is :
long number = 139454
then output should be
1.394,54
try Formatter
long number = Integer.MAX_VALUE;
System.out.printf(Locale.GERMAN, "%,.2f", new Double(number/100d) );
output
21.474.836,47
Cast the value to a double, divide it by 100 (to get the 2 decimal points) and then set the current locale to something like de_DE and use NumberFormat to format it for you.
Edit: As noted by Behrang in the comments, after converting the long to a double, it should only be used for display purposes as further calculations using this might result in loss of precision.
long number = 32301672060L;
NumberFormat nb = NumberFormat.getNumberInstance(Locale.GERMAN);
nb.setMinimumFractionDigits(2);
System.out.println(nb.format((double)number/100));
This should work for you. The German Local is important to have the point as decimal point and the comma at the last 2 digits.
Use decimals.
final BigDecimal dec = new BigDecimal(BigInteger.valueOf(32301672060L), 2);
System.out.println(new DecimalFormat("###,##0.00").format(dec));
or instead of the pattern, better to use locale's formats, e.g.
System.out.println(NumberFormat.getCurrencyInstance(Locale.US).format(dec));
or
System.out.println(NumberFormat.getNumberInstance(Locale.US).format(dec));

How can I format a String number to have commas and round?

What is the best way to format the following number that is given to me as a String?
String number = "1000500000.574" //assume my value will always be a String
I want this to be a String with the value: 1,000,500,000.57
How can I format it as such?
You might want to look at the DecimalFormat class; it supports different locales (eg: in some countries that would get formatted as 1.000.500.000,57 instead).
You also need to convert that string into a number, this can be done with:
double amount = Double.parseDouble(number);
Code sample:
String number = "1000500000.574";
double amount = Double.parseDouble(number);
DecimalFormat formatter = new DecimalFormat("#,###.00");
System.out.println(formatter.format(amount));
This can also be accomplished using String.format(), which may be easier and/or more flexible if you are formatting multiple numbers in one string.
String number = "1000500000.574";
Double numParsed = Double.parseDouble(number);
System.out.println(String.format("The input number is: %,.2f", numParsed));
// Or
String numString = String.format("%,.2f", numParsed);
For the format string "%,.2f" - "," means separate digit groups with commas, and ".2" means round to two places after the decimal.
For reference on other formatting options, see https://docs.oracle.com/javase/tutorial/java/data/numberformat.html
Given this is the number one Google result for format number commas java, here's an answer that works for people who are working with whole numbers and don't care about decimals.
String.format("%,d", 2000000)
outputs:
2,000,000
Once you've converted your String to a number, you can use
// format the number for the default locale
NumberFormat.getInstance().format(num)
or
// format the number for a particular locale
NumberFormat.getInstance(locale).format(num)
I've created my own formatting utility. Which is extremely fast at processing the formatting along with giving you many features :)
It supports:
Comma Formatting E.g. 1234567 becomes 1,234,567.
Prefixing with "Thousand(K),Million(M),Billion(B),Trillion(T)".
Precision of 0 through 15.
Precision re-sizing (Means if you want 6 digit precision, but only have 3 available digits it forces it to 3).
Prefix lowering (Means if the prefix you choose is too large it lowers it to a more suitable prefix).
The code can be found here. You call it like this:
public static void main(String[])
{
int settings = ValueFormat.COMMAS | ValueFormat.PRECISION(2) | ValueFormat.MILLIONS;
String formatted = ValueFormat.format(1234567, settings);
}
I should also point out this doesn't handle decimal support, but is very useful for integer values. The above example would show "1.23M" as the output. I could probably add decimal support maybe, but didn't see too much use for it since then I might as well merge this into a BigInteger type of class that handles compressed char[] arrays for math computations.
you can also use the below solution
public static String getRoundOffValue(double value){
DecimalFormat df = new DecimalFormat("##,##,##,##,##,##,##0.00");
return df.format(value);
}
public void convert(int s)
{
System.out.println(NumberFormat.getNumberInstance(Locale.US).format(s));
}
public static void main(String args[])
{
LocalEx n=new LocalEx();
n.convert(10000);
}
You can do the entire conversion in one line, using the following code:
String number = "1000500000.574";
String convertedString = new DecimalFormat("#,###.##").format(Double.parseDouble(number));
The last two # signs in the DecimalFormat constructor can also be 0s. Either way works.
Here is the simplest way to get there:
String number = "10987655.876";
double result = Double.parseDouble(number);
System.out.println(String.format("%,.2f",result));
output:
10,987,655.88
The first answer works very well, but for ZERO / 0 it will format as .00
Hence the format #,##0.00 is working well for me.
Always test different numbers such as 0 / 100 / 2334.30 and negative numbers before deploying to production system.
According to chartGPT
Using DecimalFormat:
DecimalFormat df = new DecimalFormat("#,###.00");
String formattedNumber = df.format(yourNumber);
Using NumberFormat:
NumberFormat nf = NumberFormat.getNumberInstance();
nf.setGroupingUsed(true);
String formattedNumber = nf.format(yourNumber);
Using String.format():
String formattedNumber = String.format("%,.2f", yourNumber);
Note: In all the above examples, "yourNumber" is the double value that you want to format with a comma. The ".2f" in the format string indicates that the decimal places should be rounded to 2 decimal places. You can adjust this value as needed.

Categories