问题
class LongDiv{
public static void main(String [] args){
final long x = 24*60*60*1000*1000;
final long y = 24*60*60*1000;
System.out.println(x/y);
}
}
although the expected answer is 1000, but the javac gives it as 5. Reason?
回答1:
The long x you are creating isn't the value you expected. It is in the integer range. To create longs, use:
final long x = 24L*60L*60L*1000L*1000L;
final long y = 24L*60L*60L*1000L;
System.out.println(x/y);
The x you computed, in the integer range, was 500654080. This divided by the y ( = 86400000), results in 5.794607407407407.... Java truncates the decimal part which causes the 5.
By adding an L after the number literal, you tell the compiler to compile it as a long instead of an int. The value for x you expected is 86400000000. But is was compiled as an int.
We can reproduce the wrong value for x (500654080) by truncating it to an int:
// First correct
long x = 24L*60L*60L*1000L*1000L;
/* x = `86400000000`; */
// Now truncate
x &= 0xFFFFFFFFL; // again: don't forget the L suffix
/* x = `500654080` */
回答2:
The expressions 24*60*60*1000*1000 is an int type not a long What you want is 24L*60*60*1000*1000 which is long
This is what you have.
final long x = (24*60*60*1000*1000) & 0xFFFFFFFF;
final long y = (24*60*60*1000) & 0xFFFFFFFF;
System.out.println(x/y);
what you want is
final long x = 24L*60*60*1000*1000;
final long y = 24L*60*60*1000;
System.out.println(x/y);
回答3:
Tricky one!
The issue is that 24, 60, and 1000 are Java literal ints. Before the values are assigned to x and y, they are truncated to fit in int values. Try
System.out.print(x + ", " + y);
to see exactly what I mean. The quick fix is to make your literals into long values like so:
public class LongDiv{
public static void main(String [] args){
final long x = 24l*60l*60l*1000l*1000l;
final long y = 24l*60l*60l*1000l;
System.out.println(x/y);
}
}
回答4:
casting (forcing) to long works in case of literal values for the right operand; but the problem persists in case of assigning one long variable to another, as in the below given example:
package utils;
public class Utils {
public static void main(String ... clps){
Utils.longDivision();
Utils.doubleDivision();
}
private static void doubleDivision(){
double x=new Long("54321").doubleValue();
double y=new Long("12345").doubleValue();
double difference=x - y;
double percentage=(difference/x)*100.00;
System.out.println("\nDouble Division ==> X : "+x+" ; Y : "+y+" ; Difference : "+difference+" ; percentage : "+percentage+"\n");
}
private static void longDivision(){
long x=new Long("54321").longValue();
long y=new Long("12345").longValue();
long difference=x - y;
long percentage=(difference/x)*100L;
System.out.println("\nLong Division ==> X : "+x+" ; Y : "+y+" ; Difference : "+difference+" ; percentage : "+percentage+"\n");
}
}
The only way i could get proper answer is by converting the division of longs into division of doubles. It is very strange why division of longs behaves in such mysterious manner.
longDivision gives the answer as zero whereas the doubleDivision gives the correct answer.
I hope this helps others who encountered similar issues...
回答5:
24*60*60*1000*1000 is too large to fit into an int and overflows.
来源:https://stackoverflow.com/questions/6766120/long-division-in-java-not-working-as-expected