How to round and scale a number using DecimalFormat - java

I'm trying to to format a number using the DecimalFormat but the problem that I didn't get the expected result. Here is the problem:
I have this number: 1439131519 and I want to print only the five first digits but with a comma after 4 digits like this: 1439,1. I have tried to use DecimalFormat but it didn't work.
I tried like this but it dosen't work:
public static DecimalFormat format2 = new DecimalFormat("0000.0");
Anyone have an idea?

It is easier to do with maths rather than formatting.
Assuming your number is in a double:
double d = 1439131519;
d = d / 100000; // d = 14391,31519
d = Math.round(d) // d = 14391
d = d / 10; // d = 1439,1
Of course, you can do it in one line of code if you want. In using Math.round I am assuming you want to round to the nearest value. If you want to round down you can use Math.floor.
The comma is the normal decimal separator in much of Europe, so that might work by default in your locale. If not, you can force it by getting the formatter for a locale such as Germany. See: How to change the decimal separator of DecimalFormat from comma to dot/point?.

Related

Java convert a format.String

I'm still new to Java and I was wondering if there are any ways to format to a double without having it rounded?
Example:
double n = 0.12876543;
String s = String.format("%1$1.2f", n);
If I were to print to the system, it would return the 0.13 instead of the precise 0.12. Now I have thought of a solution but I want to know if there is a better way of doing this. This my simple solution:
double n = 0.12876543;
double n = Double.parseDouble(String.format(("%1$1.2f", n));
Any other thoughts or solutions?
An elegant solution would be to use setRoundingMode with DecimalFormat. It sets the RoundingMode appropriately.
For example:
// Your decimal value
double n = 0.12876543;
// Decimal Formatting
DecimalFormat curDf = new DecimalFormat(".00");
// This will set the RoundingMode
curDf.setRoundingMode(RoundingMode.DOWN);
// Print statement
System.out.println(curDf.format(n));
Output:
0.12
Further, if you want to do additional formatting as a string you can always change the double value into string:
// Your decimal value
double n = 0.12876543;
// Decimal Formatting
DecimalFormat curDf = new DecimalFormat(".00");
// This will set the RoundingMode
curDf.setRoundingMode(RoundingMode.DOWN);
// Convert to string for any additional formatting
String curString = String.valueOf(curDf.format(n));
// Print statement
System.out.println(curString);
Output:
0.12
Please refer similar solution here: https://stackoverflow.com/a/8560708/4085019
As is, rounded to 2 decimals and truncated to 2 decimals :
double n = 0.12876543;
String complete = String.valueOf(n);
System.out.println(complete);
DecimalFormat df = new DecimalFormat("#.##");
String rounded = df.format(n);
System.out.println(rounded);
df.setRoundingMode(RoundingMode.DOWN);
String truncated = df.format(n);
System.out.println(truncated);
it displays :
0.12876543
0.13
0.12
Your example is working correctly in that it is properly rounding the number to 2 decimal places. 0.12876543 properly rounds to 0.13 when rounded to 2 decimal places. However, it seems like you always want to round the number down? If that is the case then you can do something like this...
public static void main(String[] args) throws IOException, InterruptedException {
double n = 0.12876543;
DecimalFormat df = new DecimalFormat("#.##");
df.setRoundingMode(RoundingMode.DOWN);
String s = df.format(n);
System.out.println(s);
}
This will print out a value of 0.12
Note first that a double is a binary fraction and does not really have decimal places.
If you need decimal places, use a BigDecimal, which has a setScale() method for truncation, or use DecimalFormat to get a String.

tinylog formatting for double values [duplicate]

I want to print a double value in Java without exponential form.
double dexp = 12345678;
System.out.println("dexp: "+dexp);
It shows this E notation: 1.2345678E7.
I want it to print it like this: 12345678
What is the best way to prevent this?
Java prevent E notation in a double:
Five different ways to convert a double to a normal number:
import java.math.BigDecimal;
import java.text.DecimalFormat;
public class Runner {
public static void main(String[] args) {
double myvalue = 0.00000021d;
//Option 1 Print bare double.
System.out.println(myvalue);
//Option2, use decimalFormat.
DecimalFormat df = new DecimalFormat("#");
df.setMaximumFractionDigits(8);
System.out.println(df.format(myvalue));
//Option 3, use printf.
System.out.printf("%.9f", myvalue);
System.out.println();
//Option 4, convert toBigDecimal and ask for toPlainString().
System.out.print(new BigDecimal(myvalue).toPlainString());
System.out.println();
//Option 5, String.format
System.out.println(String.format("%.12f", myvalue));
}
}
This program prints:
2.1E-7
.00000021
0.000000210
0.000000210000000000000001085015324114868562332958390470594167709350585
0.000000210000
Which are all the same value.
Protip: If you are confused as to why those random digits appear beyond a certain threshold in the double value, this video explains: computerphile why does 0.1+0.2 equal 0.30000000000001?
http://youtube.com/watch?v=PZRI1IfStY0
You could use printf() with %f:
double dexp = 12345678;
System.out.printf("dexp: %f\n", dexp);
This will print dexp: 12345678.000000. If you don't want the fractional part, use
System.out.printf("dexp: %.0f\n", dexp);
0 in %.0f means 0 places in fractional part i.e no fractional part. If you want to print fractional part with desired number of decimal places then instead of 0 just provide the number like this %.8f. By default fractional part is printed up to 6 decimal places.
This uses the format specifier language explained in the documentation.
The default toString() format used in your original code is spelled out here.
In short:
If you want to get rid of trailing zeros and Locale problems, then you should use:
double myValue = 0.00000021d;
DecimalFormat df = new DecimalFormat("0", DecimalFormatSymbols.getInstance(Locale.ENGLISH));
df.setMaximumFractionDigits(340); // 340 = DecimalFormat.DOUBLE_FRACTION_DIGITS
System.out.println(df.format(myValue)); // Output: 0.00000021
Explanation:
Why other answers did not suit me:
Double.toString() or System.out.println or FloatingDecimal.toJavaFormatString uses scientific notations if double is less than 10^-3 or greater than or equal to 10^7
By using %f, the default decimal precision is 6, otherwise you can hardcode it, but it results in extra zeros added if you have fewer decimals. Example:
double myValue = 0.00000021d;
String.format("%.12f", myvalue); // Output: 0.000000210000
By using setMaximumFractionDigits(0); or %.0f you remove any decimal precision, which is fine for integers/longs, but not for double:
double myValue = 0.00000021d;
System.out.println(String.format("%.0f", myvalue)); // Output: 0
DecimalFormat df = new DecimalFormat("0");
System.out.println(df.format(myValue)); // Output: 0
By using DecimalFormat, you are local dependent. In French locale, the decimal separator is a comma, not a point:
double myValue = 0.00000021d;
DecimalFormat df = new DecimalFormat("0");
df.setMaximumFractionDigits(340);
System.out.println(df.format(myvalue)); // Output: 0,00000021
Using the ENGLISH locale makes sure you get a point for decimal separator, wherever your program will run.
Why using 340 then for setMaximumFractionDigits?
Two reasons:
setMaximumFractionDigits accepts an integer, but its implementation has a maximum digits allowed of DecimalFormat.DOUBLE_FRACTION_DIGITS which equals 340
Double.MIN_VALUE = 4.9E-324 so with 340 digits you are sure not to round your double and lose precision.
You can try it with DecimalFormat. With this class you are very flexible in parsing your numbers.
You can exactly set the pattern you want to use.
In your case for example:
double test = 12345678;
DecimalFormat df = new DecimalFormat("#");
df.setMaximumFractionDigits(0);
System.out.println(df.format(test)); //12345678
I've got another solution involving BigDecimal's toPlainString(), but this time using the String-constructor, which is recommended in the javadoc:
this constructor is compatible with the values returned by Float.toString and Double.toString. This is generally the preferred way to convert a float or double into a BigDecimal, as it doesn't suffer from the unpredictability of the BigDecimal(double) constructor.
It looks like this in its shortest form:
return new BigDecimal(myDouble.toString()).stripTrailingZeros().toPlainString();
NaN and infinite values have to be checked extra, so looks like this in its complete form:
public static String doubleToString(Double d) {
if (d == null)
return null;
if (d.isNaN() || d.isInfinite())
return d.toString();
return new BigDecimal(d.toString()).stripTrailingZeros().toPlainString();
}
This can also be copied/pasted to work nicely with Float.
For Java 7 and below, this results in "0.0" for any zero-valued Doubles, so you would need to add:
if (d.doubleValue() == 0)
return "0";
Java/Kotlin compiler converts any value greater than 9999999 (greater than or equal to 10 million) to scientific notation ie. Epsilion notation.
Ex: 12345678 is converted to 1.2345678E7
Use this code to avoid automatic conversion to scientific notation:
fun setTotalSalesValue(String total) {
var valueWithoutEpsilon = total.toBigDecimal()
/* Set the converted value to your android text view using setText() function */
salesTextView.setText( valueWithoutEpsilon.toPlainString() )
}
This will work as long as your number is a whole number:
double dnexp = 12345678;
System.out.println("dexp: " + (long)dexp);
If the double variable has precision after the decimal point it will truncate it.
I needed to convert some double to currency values and found that most of the solutions were OK, but not for me.
The DecimalFormat was eventually the way for me, so here is what I've done:
public String foo(double value) //Got here 6.743240136E7 or something..
{
DecimalFormat formatter;
if(value - (int)value > 0.0)
formatter = new DecimalFormat("0.00"); // Here you can also deal with rounding if you wish..
else
formatter = new DecimalFormat("0");
return formatter.format(value);
}
As you can see, if the number is natural I get - say - 20000000 instead of 2E7 (etc.) - without any decimal point.
And if it's decimal, I get only two decimal digits.
I think everyone had the right idea, but all answers were not straightforward.
I can see this being a very useful piece of code. Here is a snippet of what will work:
System.out.println(String.format("%.8f", EnterYourDoubleVariableHere));
the ".8" is where you set the number of decimal places you would like to show.
I am using Eclipse and it worked no problem.
Hope this was helpful. I would appreciate any feedback!
The following code detects if the provided number is presented in scientific notation. If so it is represented in normal presentation with a maximum of '25' digits.
static String convertFromScientificNotation(double number) {
// Check if in scientific notation
if (String.valueOf(number).toLowerCase().contains("e")) {
System.out.println("The scientific notation number'"
+ number
+ "' detected, it will be converted to normal representation with 25 maximum fraction digits.");
NumberFormat formatter = new DecimalFormat();
formatter.setMaximumFractionDigits(25);
return formatter.format(number);
} else
return String.valueOf(number);
}
This may be a tangent.... but if you need to put a numerical value as an integer (that is too big to be an integer) into a serializer (JSON, etc.) then you probably want "BigInterger"
Example:
value is a string - 7515904334
We need to represent it as a numerical in a Json message:
{
"contact_phone":"800220-3333",
"servicer_id":7515904334,
"servicer_name":"SOME CORPORATION"
}
We can't print it or we'll get this:
{
"contact_phone":"800220-3333",
"servicer_id":"7515904334",
"servicer_name":"SOME CORPORATION"
}
Adding the value to the node like this produces the desired outcome:
BigInteger.valueOf(Long.parseLong(value, 10))
I'm not sure this is really on-topic, but since this question was my top hit when I searched for my solution, I thought I would share here for the benefit of others, lie me, who search poorly. :D
use String.format ("%.0f", number)
%.0f for zero decimal
String numSring = String.format ("%.0f", firstNumber);
System.out.println(numString);
I had this same problem in my production code when I was using it as a string input to a math.Eval() function which takes a string like "x + 20 / 50"
I looked at hundreds of articles... In the end I went with this because of the speed. And because the Eval function was going to convert it back into its own number format eventually and math.Eval() didn't support the trailing E-07 that other methods returned, and anything over 5 dp was too much detail for my application anyway.
This is now used in production code for an application that has 1,000+ users...
double value = 0.0002111d;
String s = Double.toString(((int)(value * 100000.0d))/100000.0d); // Round to 5 dp
s display as: 0.00021
This will work not only for a whole numbers:
double dexp = 12345678.12345678;
BigDecimal bigDecimal = new BigDecimal(Double.toString(dexp));
System.out.println("dexp: "+ bigDecimal.toPlainString());
My solution:
String str = String.format ("%.0f", yourDouble);
For integer values represented by a double, you can use this code, which is much faster than the other solutions.
public static String doubleToString(final double d) {
// check for integer, also see https://stackoverflow.com/a/9898613/868941 and
// https://github.com/google/guava/blob/master/guava/src/com/google/common/math/DoubleMath.java
if (isMathematicalInteger(d)) {
return Long.toString((long)d);
} else {
// or use any of the solutions provided by others, this is the best
DecimalFormat df =
new DecimalFormat("0", DecimalFormatSymbols.getInstance(Locale.ENGLISH));
df.setMaximumFractionDigits(340); // 340 = DecimalFormat.DOUBLE_FRACTION_DIGITS
return df.format(d);
}
}
// Java 8+
public static boolean isMathematicalInteger(final double d) {
return StrictMath.rint(d) == d && Double.isFinite(d);
}
This works for me. The output will be a String.
String.format("%.12f", myvalue);
Good way to convert scientific e notation
String.valueOf(YourDoubleValue.longValue())

Formatting string number into double variable with two number after decimal point

I'm getting from server a string value formatted as follow: 14.5000
I need to create a double variable from it with two number after decimal point: 14.50. I've tried the following:
DecimalFormat df = new DecimalFormat("#,00");
Double priceD = Double.parseDouble((produitParam.item(paramNb).getTextContent()));
String dx = df.format(priceD);
produit.setPrixTtc(Double.valueOf(dx));
And I'm getting 14.5. If I use DecimalFormat("#.00"), it gives me 15...
Someone could help me with that ?
If you want string with precision upto 2 points after decimal you should use
DecimalFormat df = new DecimalFormat("#.00");
you have used "#,00"
',' is used for specifying grouping Separator.
for more information here is the Java Doc of DecimalFormat:
http://docs.oracle.com/javase/7/docs/api/java/text/DecimalFormat.html
you should look this link.There is a lot of answer your question.
I think.The best answer is DecimalFormat df = new DecimalFormat("#0.00");
for you in link
[how to convert double to 2 number after the dot?

Double value with specific precision in java

I'm programming a simple java program. I need to get a string from input and divide it into two parts: 1-double 2-string.
Then I need to do a simple calculation on the double and send the result to the output with specific precision(4). It works fine, but there is a problem when the input is 0, then it doesn't work properly.
For example for these input, output will be:
1 kg
output:2.2046
3.1 kg
output:6.8343
But when the input is 0, the output should be 0.0000, but it shows 0.0 .
What should I do to force it to show 0.0000?
I read similar post about double precision, they suggest something like BigDecimal class, but I can't use them in this case,
my code for doing this is:
line=input.nextLine();
array=line.split(" ");
value=Double.parseDouble(array[0]);
type=array[1];
value =value*2.2046;
String s = String.format("%.4f", value);
value = Double.parseDouble(s);
System.out.print(value+" kg\n");
DecimalFormat will allow you to define how many digits you want to display. A '0' will force an output of digits even if the value is zero, whereas a '#' will omit zeros.
System.out.print(new DecimalFormat("#0.0000").format(value)+" kg\n"); should to the trick.
See the documentation
Note: if used frequently, for performance reasons you should instantiate the formatter only once and store the reference: final DecimalFormat df = new DecimalFormat("#0.0000");. Then use df.format(value).
add this instance of DecimalFormat to the top of your method:
DecimalFormat four = new DecimalFormat("#0.0000"); // will round and display the number to four decimal places. No more, no less.
// the four zeros after the decimal point above specify how many decimal places to be accurate to.
// the zero to the left of the decimal place above makes it so that numbers that start with "0." will display "0.____" vs just ".____" If you don't want the "0.", replace that 0 to the left of the decimal point with "#"
then, call the instance "four" and pass your double value when displaying:
double value = 0;
System.out.print(four.format(value) + " kg/n"); // displays 0.0000
System.out.format("%.4f kg\n", 0.0d) prints '0.0000 kg'
I suggest you to use the BigDecimal class for calculating with floating point values. You will be able to control the precision of the floating point arithmetic. But back to the topic :)
You could use the following:
static void test(String stringVal) {
final BigDecimal value = new BigDecimal(stringVal).multiply(new BigDecimal("2.2046"));
DecimalFormat df = new DecimalFormat();
df.setMaximumFractionDigits(4);
df.setMinimumFractionDigits(4);
System.out.println(df.format(value) + " kg\n");
}
public static void main(String[] args) {
test("0");
test("1");
test("3.1");
}
will give you the following output:
0,0000 kg
2,2046 kg
6,8343 kg
String.format is just makign a String representation of the floating point value. If it doesnt provide a flag for a minimum precision, then just pad the end of the string with zeros.
Use DecimalFormat to format your double value to fixed precision string output.
DecimalFormat is a concrete subclass of NumberFormat that formats
decimal numbers. It has a variety of features designed to make it
possible to parse and format numbers in any locale, including support
for Western, Arabic, and Indic digits. It also supports different
kinds of numbers, including integers (123), fixed-point numbers
(123.4), scientific notation (1.23E4), percentages (12%), and currency
amounts ($123). All of these can be localized.
Example -
System.out.print(new DecimalFormat("##.##").format(value)+" kg\n");

Convert a number to 2 decimal places in Java

I want to convert a number to a 2 decimal places (Always show two decimal places) in runtime. I tried some code but it only does, as shown below
20.03034 >> 20.03
20.3 >> 20.3 ( my code only rounds not converts )
however, I want it to do this:
20.03034 >> 20.03
20.3 >> 20.30 (convert it to two decimal places)
My code below:
angle = a variable
angle_screen = a variable
DecimalFormat df = new DecimalFormat("#.##");
angle = Double.valueOf(df.format(angle));
angle_screen.setText(String.valueOf(angle) + tmp);
Any help on how to do this would be great, thanks.
try this new DecimalFormat("#.00");
update:
double angle = 20.3034;
DecimalFormat df = new DecimalFormat("#.00");
String angleFormated = df.format(angle);
System.out.println(angleFormated); //output 20.30
Your code wasn't using the decimalformat correctly
The 0 in the pattern means an obligatory digit, the # means optional digit.
update 2: check bellow answer
If you want 0.2677 formatted as 0.27 you should use new DecimalFormat("0.00"); otherwise it will be .27
DecimalFormat df=new DecimalFormat("0.00");
Use this code to get exact two decimal points.
Even if the value is 0.0 it will give u 0.00 as output.
Instead if you use:
DecimalFormat df=new DecimalFormat("#.00");
It wont convert 0.2659 into 0.27. You will get an answer like .27.
Try this: String.format("%.2f", angle);
Try
DecimalFormat df = new DecimalFormat("#,##0.00");

Categories