I have a float value of a current weight like e.g. "79.3" kilograms.
I split the float value into a kilogram and a grams value.
I get the right amount of kilograms when parsing the float-value to int.
Then I get the fractional part of the float-value. This fractional part looks like "0,3" which means 0.3 kilograms or 300grams.
In my Programm I can only have 0,100,200,..,900 Grams which would stand for 0-9.
My goal is to remove the "0," so I only get the value of "3".
This is my code for now and I tried some decimal formatting too, but I didn't know how to do it:
public void setCurrentWeightInTheNumberPickers() {
float currentWeightAsFloat = weight_dbHandler.getCurrentWeightFloat();
int currentWeightKilograms = (int) currentWeightAsFloat;
double fractionOfGrams = currentWeightAsFloat % 1;
DecimalFormat df1 = new DecimalFormat("0.##");
String rounded = df1.format(fractionOfGrams);
rounded.replaceFirst("^0+(?!$)", "");
} //public void setCurrentWeightInTheNumberPickers()
Given a string
String gram = "0,3";
you can just do:
gram = gram.substring(gram.lastIndexOf(",") + 1);
which gives the following output when printed
3
Or you can simply do that. No need for strings.
float f = 3.3f;
int g = (int)f;
int h = Math.round((f - g)*10);
and since h is supposed to be grams, you might as well make it *1000
I view this primarily as a math, not a Java, problem. Given a float input in units of kilograms, to obtain only the kilogram component, we can take the floor. To get the grams component, we can multiply by 1000 and then take the mod of 1000.
double input = 79.321;
double kg = Math.floor(input);
System.out.println("kilograms: " + kg);
double g = Math.floor((1000*input) % 1000);
System.out.println("grams: " + g);
kilograms: 79.0
grams: 321.0
Note: I am using double here instead of float, only because Math.floor returns double as its return value.
Related
I have read this question Round a double to 2 decimal places It shows how to round number. What I want is just simple formatting, printing only two decimal places.
What I have and what I tried:
double res = 24.695999999999998;
DecimalFormat df = new DecimalFormat("####0.00");
System.out.println("Value: " + df.format(res)); //prints 24.70 and I want 24.69
System.out.println("Total: " + String.format( "%.2f", res )); //prints 24.70
So when I have 24.695999999999998 I want to format it as 24.69
You need to take the floor of the double value first - then format it.
Math.floor(double)
Returns the largest (closest to positive infinity) double value that is less than or equal to the argument and is equal to a mathematical integer.
So use something like:
double v = Math.floor(res * 100) / 100.0;
Other alternatives include using BigDecimal.
public void test() {
double d = 0.29;
System.out.println("d=" + d);
System.out.println("floor(d*100)/100=" + Math.floor(d * 100) / 100);
System.out.println("BigDecimal d=" + BigDecimal.valueOf(d).movePointRight(2).round(MathContext.UNLIMITED).movePointLeft(2));
}
prints
d=0.29
floor(d*100)/100=0.28
BigDecimal d=0.29
Multiply the number by 100 and cast it to an integer. This cuts off all the decimal spaces except the two you want. Divide the result by 100.00. (24.69).
int temp = (int)(res * 100);
double result = temp / 100.00;
or the same thing in one line of code:
double result = ((int)(res * 100)) / 100.00;
In addition to using Math.floor(double) and calculating a scale (e.g. * 100 and then / 100.0 for two decimal points) you could use BigDecimal, then you can invoke setScale(int, int) like
double res = 24.695999999999998;
BigDecimal bd = BigDecimal.valueOf(res);
bd = bd.setScale(2, RoundingMode.DOWN);
System.out.println("Value: " + bd);
Which will also give you (the requested)
Value: 24.69
I'm trying to write a program that converts kilograms to pounds and ounces. If the user enters 100 kilograms the result I'm expecting is 220 pounds and 7.4 ounces.
I get the correct pound value but my problem is getting the correct ounces value. I don't know what I'm missing. Also when I calculate the ounces value, how do i specify to the program that I only want the answer to the hundredth degree. For example I only want 7.4 ounces and not 7.4353?
import acm.program.*;
public class KilogramsToPoundsAndOunces extends ConsoleProgram {
public void run() {
println("This program converts Kilograms into Pounds and Ounces.");
int kilo = readInt("please enter a number in kilograms: ");
double lbs = kilo * POUNDS_PER_KILOGRAM;
double oz = lbs * OUNCES_PER_POUND;
double endPounds = (int) oz / OUNCES_PER_POUND;
double endOunces = oz - (endPounds * OUNCES_PER_POUND);
println( endPounds + " lbs " + endOunces + "ozs");
}
private static final double POUNDS_PER_KILOGRAM = 2.2;
private static final int OUNCES_PER_POUND = 16;
}
The easiest way would be to use System.out.printf and format the output there:
System.out.printf("%d lbs %.1f ozs", endPounds, endOunces);
If you can't use System.out.printf, you can still use String#format to format the output:
println(String.format("%d lbs %.1f ozs", endPounds, endOunces));
Cases where you need exact decimal value; its better to use BigDecimal data type instead of double.
The BigDecimal class provides operations for arithmetic, scale manipulation, rounding, comparison, hashing, and format conversion. link
BigDecimal provides methods to round the number to given value.
Use DecimalFormat to print the decimal places in desired format e.g.
DecimalFormat dFormat = new DecimalFormat("#.0");
System.out.println( endPounds + " lbs " + dFormat.format(endOunces) + " ozs");
If you want rounding done upto one decimal place, then multiply the number by 10, round, then divide again and print as below:
double roundedOunces = Math.round(endOunces*10)/10.0;
DecimalFormat dFormat = new DecimalFormat("#.0");
System.out.println( endPounds + " lbs " + dFormat.format(roundedOunces) + " ozs");
EDIT:
Try this for rounding:
double roundedOunces = Math.round(endOunces*10)/10.0;.
Without rounding:
double roundedOunces = endOunces*10/10.0;
Here is my code. For some reason my BMI is not calculated correctly.
When I check the output on a calculator for this : (10/((10/100)^2))) I get 1000, but in my program, I get 5. I'm not sure what I am doing wrong. Here is my code:
import javax.swing.*;
public class BMI {
public static void main(String args[]) {
int height;
int weight;
String getweight;
getweight = JOptionPane.showInputDialog(null, "Please enter your weight in Kilograms");
String getheight;
getheight = JOptionPane.showInputDialog(null, "Please enter your height in Centimeters");
weight = Integer.parseInt(getweight);
height = Integer.parseInt(getheight);
double bmi;
bmi = (weight/((height/100)^2));
JOptionPane.showMessageDialog(null, "Your BMI is: " + bmi);
}
}
^ in java does not mean to raise to a power. It means XOR.
You can use java's Math.pow()
And you might want to consider using double instead of int—that is:
double height;
double weight;
Note that 199/100 evaluates to 1.
we can use
Math.pow(2, 4);
this mean 2 to the power 4 (2^4)
answer = 16
^ is not the operator you want. You are looking for the pow method of java.lang.Math.
You can use Math.pow(value, power).
Example:
Math.pow(23, 5); // 23 to the fifth power
Your calculation is likely the culprit. Try using:
bmi = weight / Math.pow(height / 100.0, 2.0);
Because both height and 100 are integers, you were likely getting the wrong answer when dividing. However, 100.0 is a double. I suggest you make weight a double as well. Also, the ^ operator is not for powers. Use the Math.pow() method instead.
Too late for the OP of course, but still...
Rearranging the expression as:
int bmi = (10000 * weight) / (height * height)
Eliminates all the floating point, and converts a division by a constant to a multiplication, which should execute faster. Integer precision is probably adequate for this application, but if it is not then:
double bmi = (10000.0 * weight) / (height * height)
would still be an improvement.
You should use below method-
Math.pow(double a, double b)
From (https://docs.oracle.com/javase/8/docs/api/java/lang/Math.html#pow-double-double-)
Returns the value of the first argument raised to the power of the second argument.
int weight=10;
int height=10;
double bmi;
bmi = weight / Math.pow(height / 100.0, 2.0);
System.out.println("bmi"+(bmi));
double result = bmi * 100;
result = Math.round(result);
result = result / 100;
System.out.println("result"+result);
1) We usually do not use int data types to height, weight, distance,
temperature etc.(variables which can have decimal points)
Therefore height, weight should be double or float.
but double is more accurate than float when you have more decimal points
2) And instead of ^, you can change that calculation as below using Math.pow()
bmi = (weight/(Math.pow(height/100, 2)));
3) Math.pow() method has below definition
Math.pow(double var_1, double var_2);
Example:
i) Math.pow(8, 2) is produced 64 (8 to the power 2)
ii) Math.pow(8.2, 2.1) is produced 82.986813689753 (8.2 to the power 2.1)
I did the benchmarking with Math.pow(x,2) and x*x,
the result is that Math.pow() is easily forty times slower than manually multiplying it by itself, so i don't recommend it for anything where a little bit of performance is required.
Here's the results:
proof_of_work: 19.284756867003345
time for Math.pow(x,2) in ns: 35143
proof_of_work: 19.284756867003345
time for x*x in ns: 884
manual calculation is 39 times faster
and here's the test-code
double r1 = 4.391441320;
long multiply_d1 = System.nanoTime();
double multiply_dr = Math.pow(r1,2);
long multiply_d2 = System.nanoTime();
System.out.println(("proof_of_work: ") + (multiply_dr));
System.out.println(("time for Math.pow(x,2) in ns: ") + (multiply_d2 - multiply_d1));
long multiply_t1 = System.nanoTime();
double multiply_tr = r1*r1;
long multiply_t2 = System.nanoTime();
System.out.println(("proof_of_work: ") + (multiply_tr));
System.out.println(("time for x*x in ns: ") + (multiply_t2 - multiply_t1));
System.out.println(("manual calculation is ") + ((multiply_d2 - multiply_d1) / (multiply_t2 - multiply_t1)) + (" times faster"));
Most efficient solution is
public Float fastPow(Float number, Integer power) {
if (power == 0) {
return 1.0f;
} else if (power % 2 == 1) {
return fastPow(number, power - 1) * number;
} else {
return fastPow(number * number, power / 2);
}
}
Let A is our number and N our power. Then A^2^N = (A^2)^N. And A^N = (A^2)^N/2. The function above reflects this relationship.
For example I have the variable 3.545555555, which I would want to truncate to just 3.54.
If you want that for display purposes, use java.text.DecimalFormat:
new DecimalFormat("#.##").format(dblVar);
If you need it for calculations, use java.lang.Math:
Math.floor(value * 100) / 100;
DecimalFormat df = new DecimalFormat(fmt);
df.setRoundingMode(RoundingMode.DOWN);
s = df.format(d);
Check available RoundingMode and DecimalFormat.
None of the other answers worked for both positive and negative values ( I mean for the calculation and just to do "truncate" without Rounding). and without converting to string.
From the How to round a number to n decimal places in Java link
private static BigDecimal truncateDecimal(double x,int numberofDecimals)
{
if ( x > 0) {
return new BigDecimal(String.valueOf(x)).setScale(numberofDecimals, BigDecimal.ROUND_FLOOR);
} else {
return new BigDecimal(String.valueOf(x)).setScale(numberofDecimals, BigDecimal.ROUND_CEILING);
}
}
This method worked fine for me .
System.out.println(truncateDecimal(0, 2));
System.out.println(truncateDecimal(9.62, 2));
System.out.println(truncateDecimal(9.621, 2));
System.out.println(truncateDecimal(9.629, 2));
System.out.println(truncateDecimal(9.625, 2));
System.out.println(truncateDecimal(9.999, 2));
System.out.println(truncateDecimal(-9.999, 2));
System.out.println(truncateDecimal(-9.0, 2));
Results :
0.00
9.62
9.62
9.62
9.62
9.99
-9.99
-9.00
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.
Formating as a string and converting back to double i think will give you the result you want.
The double value will not be round(), floor() or ceil().
A quick fix for it could be:
String sValue = (String) String.format("%.2f", oldValue);
Double newValue = Double.parseDouble(sValue);
You can use the sValue for display purposes or the newValue for calculation.
If, for whatever reason, you don't want to use a BigDecimal you can cast your double to an int to truncate it.
If you want to truncate to the Ones place:
simply cast to int
To the Tenths place:
multiply by ten
cast to int
cast back to double
and divide by ten.
Hundreths place
multiply and divide by 100 etc.
Example:
static double truncateTo( double unroundedNumber, int decimalPlaces ){
int truncatedNumberInt = (int)( unroundedNumber * Math.pow( 10, decimalPlaces ) );
double truncatedNumber = (double)( truncatedNumberInt / Math.pow( 10, decimalPlaces ) );
return truncatedNumber;
}
In this example, decimalPlaces would be the number of places PAST the ones place you wish to go, so 1 would round to the tenths place, 2 to the hundredths, and so on (0 rounds to the ones place, and negative one to the tens, etc.)
You can use NumberFormat Class object to accomplish the task.
// Creating number format object to set 2 places after decimal point
NumberFormat nf = NumberFormat.getInstance();
nf.setMaximumFractionDigits(2);
nf.setGroupingUsed(false);
System.out.println(nf.format(precision));// Assuming precision is a double type variable
3.545555555 to get 3.54.
Try Following for this:
DecimalFormat df = new DecimalFormat("#.##");
df.setRoundingMode(RoundingMode.FLOOR);
double result = new Double(df.format(3.545555555);
This will give= 3.54!
Maybe Math.floor(value * 100) / 100? Beware that the values like 3.54 may be not exactly represented with a double.
Here is the method I use:
double a=3.545555555; // just assigning your decimal to a variable
a=a*100; // this sets a to 354.555555
a=Math.floor(a); // this sets a to 354
a=a/100; // this sets a to 3.54 and thus removing all your 5's
This can also be done:
a=Math.floor(a*100) / 100;
I used Math.floor() method and basic moving of decimal places by (100 = 2).
//3.545555555 to 3.54 by floor method
double x = 3.545555555;
double y = Math.floor(x * 100); //354
double z = y / 100; //3.54
Maybe following :
double roundTwoDecimals(double d) {
DecimalFormat twoDForm = new DecimalFormat("#.##");
return Double.valueOf(twoDForm.format(d));
}
I have a slightly modified version of Mani's.
private static BigDecimal truncateDecimal(final double x, final int numberofDecimals) {
return new BigDecimal(String.valueOf(x)).setScale(numberofDecimals, BigDecimal.ROUND_DOWN);
}
public static void main(String[] args) {
System.out.println(truncateDecimal(0, 2));
System.out.println(truncateDecimal(9.62, 2));
System.out.println(truncateDecimal(9.621, 2));
System.out.println(truncateDecimal(9.629, 2));
System.out.println(truncateDecimal(9.625, 2));
System.out.println(truncateDecimal(9.999, 2));
System.out.println(truncateDecimal(3.545555555, 2));
System.out.println(truncateDecimal(9.0, 2));
System.out.println(truncateDecimal(-9.62, 2));
System.out.println(truncateDecimal(-9.621, 2));
System.out.println(truncateDecimal(-9.629, 2));
System.out.println(truncateDecimal(-9.625, 2));
System.out.println(truncateDecimal(-9.999, 2));
System.out.println(truncateDecimal(-9.0, 2));
System.out.println(truncateDecimal(-3.545555555, 2));
}
Output:
0.00
9.62
9.62
9.62
9.62
9.99
9.00
3.54
-9.62
-9.62
-9.62
-9.62
-9.99
-9.00
-3.54
A quick check is to use the Math.floor method. I created a method to check a double for two or less decimal places below:
public boolean checkTwoDecimalPlaces(double valueToCheck) {
// Get two decimal value of input valueToCheck
double twoDecimalValue = Math.floor(valueToCheck * 100) / 100;
// Return true if the twoDecimalValue is the same as valueToCheck else return false
return twoDecimalValue == valueToCheck;
}
double value = 3.4555;
String value1 = String.format("% .3f", value) ;
String value2 = value1.substring(0, value1.length() - 1);
System.out.println(value2);
double doublevalue= Double.valueOf(value2);
System.out.println(doublevalue);
double firstValue = -3.1756d;
double value1 = (((int)(Math.pow(10,3)*firstValue))/Math.pow(10,3));
In this solution, this will TRUNCATE a double to only two decimal places. This solution will not ROUND OFF the double value.
double myDoubleNumber = 3.545555555;
DecimalFormat df = new DecimalFormat("#.##");
df.setRoundingMode(RoundingMode.DOWN);
double myDoubleNumberTruncated = Double.parseDouble(df.format(myDoubleNumber));
System.out.println(myDoubleNumberTruncated);
This will output 3.54
DecimalFormat("#.##") - Here, I entered two hash symbols(##) after the decimal point. Hence, this will truncate the number up to two decimal places.
This will work for both Positive & Negative values.
This worked for me:
double input = 104.8695412 //For example
long roundedInt = Math.round(input * 100);
double result = (double) roundedInt/100;
//result == 104.87
I personally like this version because it actually performs the rounding numerically, rather than by converting it to a String (or similar) and then formatting it.
I have a double variable test. I want to extract the all digits before decimal point and two digits after the decimal point store the output in integer variables dollar, cents. how can i do it? I dont want any rounding to happen.
example:
double test= 12.1234
Output
int dollar =12;
int cents =12;
double test =1235.0
output
int dollar=1235
int cents =0
For currency, especially when you don't want any rounding, you should use the BigDecimal class. Something like:
BigDecimal test = new BigDecimal("12.1234");
int dollar = test.intValue();
int cents = test.scaleByPowerOfTen(2).intValue() - dollar * 100;
You can do:
double test= 12.1234;
int dollar = (int) test;
int cents = (int) ((test-dollar) * 100);
How about:
dollar = test;
test -= dollar;
cents = test * 100;
Line 1 assigns the integer part of test (12) to the integer 'dollar.'
Line 2 removes the 12 dollars from the test value.
Line 3 assigns 100 times the fractional part of test to cents. Note that I don't round here. For that, you'd have to:
cents = (test + 0.005) * 100
How about something like this. Rather than printing the values, you can simply assign them as you see fit.
double d = 32.456;
System.out.println( (int)d );
System.out.println( d-(int)d);
String[] s = Double.toString(test).split(".");
String dol = s[0];
String cent = s[1].substring(0,1);
For double values greater than 10^13, there won't be ANY significant digits after the notional decimal point.
You should not be using double or float for representing financial quantities. Use int or long (appropriately scaled and with explicit checks for overflow) or BigDecimal.