为什么这两个乘法运算会给出不同的结果? [英] Why do these two multiplication operations give different results?

查看:31
本文介绍了为什么这两个乘法运算会给出不同的结果?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

为什么我需要添加一个L"字母才能获得正确的长值?另一个值是什么?

Why do I need to add an "L" letter to get the correct long value? And what is the other value?

long oneYearWithL = 1000*60*60*24*365L;
long oneYearWithoutL = 1000*60*60*24*365;
System.out.println(oneYearWithL);//gives correct calculation result : 31536000000
System.out.println(oneYearWithoutL)//gives incorrect calculation result: 1471228928

推荐答案

long oneYearWithL = 1000*60*60*24*365L;
long oneYearWithoutL = 1000*60*60*24*365;

你的第一个值实际上是一个长(因为 365L 是一个 long,而 1000*60*60*24 是一个 integer,所以乘以一个long值与一个integer值的结果是一个long价值.

Your first value is actually a long (Since 365L is a long, and 1000*60*60*24 is an integer, so the result of multiplying a long value with an integer value is a long value.

但是第二个值是一个整数(因为你只是将一个 integer 值与一个 integer 值相乘.所以结果将是一个 32-bit 整数.现在该 乘法 获得的结果超出了整数的实际范围.因此,在分配给变量之前,它会被截断以适应有效的整数范围.

But 2nd value is an integer (Since you are mulitplying an integer value with an integer value only. So the result will be a 32-bit integer. Now the result obtained for that multiplication is outside the actual range of integer. So, before getting assigned to the variable, it is truncated to fit into valid integer range.

看看下面的打印语句:-

Take a look at the following print statement: -

System.out.println(1000*60*60*24*365L);
System.out.println(1000*60*60*24*365);
System.out.println(Integer.MAX_VALUE);

当你运行上面的代码时: -

When you run the above code: -

输出:-

31536000000
1471228928
2147483647

所以,你可以看到差异..

So, you can see the difference..

011101010111101100010010110000000000 -- Binary equivalent of 1000*60*60*24*365L
    01111111111111111111111111111111 -- Binary equivalent of Integer.MAX_VALUE

因此,如果您不在数字末尾添加 L,则会从第一个二进制字符串中删除 4 个最高有效位.

So, if you don't add that L at the end of your number, the 4 most significant bit is removed from the first binary string..

所以,字符串变成..

(0111)01010111101100010010110000000000 -- Remove the most significant bits..
      01010111101100010010110000000000 -- Binary equivalent of 1471228928

(你得到的输出)

更新:-从上面的解释,你也可以理解,即使在第一次赋值中,如果你的乘法integers的结果在乘以365L之前> 超出范围,然后再次将其截断以适合整数范围,或根据需要转换为 2 的补码表示,然后仅将其与 long 值相乘 - 365L.

UPDATE: - From the above explanation, you can also understand that, even in the first assignment, if the result of your multiplication of integers before multiplying it with 365L goes out of range, then again it will be truncated to fit in integer range, or converted to 2's complement representation if required, and then only it will be multiplied with the long value - 365L.

例如:-

long thirtyYearWithL = 1000*60*60*24*30*365L;

在上面的例子中,考虑第一部分 - 1000*60*60*24*30.这个乘法的结果是: - 2592000000.现在让我们看看它是如何用二进制等价物表示的:-

In the above example, consider the first part - 1000*60*60*24*30. The result of this multiplication is: - 2592000000. Now lets' see how it is represented in binary equivalent: -

2592000000 = 10011010011111101100100000000000  -- MSB is `1`, a negative value
             01100101100000010011100000000001  -- 2's complement representation

2 的补码 表示的十进制表示为 1702967297.因此,2592000000 在乘以 365L 之前被转换为 -1702967297.现在,这个值适合整数范围,即:-[-2147483648 to 2147483647],所以它不会被进一步截断.

Decimal representation of the 2's complement representation is 1702967297. So, 2592000000 is converted to -1702967297, before getting multiplied to 365L. Now since, this value fits in the integer range which is : - [-2147483648 to 2147483647], so it will not be truncated further.

所以,实际结果将是:-

So, the actual result will be: -

long thirtyYearWithL = 1000*60*60*24*30*365L;
                     = 2592000000 * 365L;
                     = -1702967297 * 365L = -621583063040

所以,所有这些东西都只考虑应用算术运算的最终结果的实际type.并且对从 left-to-right 移动的操作的每个临时结果执行此检查(考虑具有 left-to-right 关联性的运算符).如果发现任何临时结果超出范围,则相应地将其转换为适合所需范围,然后再进行下一步操作.

So, all these stuffs just considers the actual type of final result on applying the arithmetic operation. And this check is performed on each temporary result of operations moving from left to right(considering operators with left-to-right associativity). If any temporary result is found to be out of range, then that is converted accordingly to fit in the required range, before moving forward with next operation.

更新 2:-

所以,而不是:-

long thirtyYearWithL = 1000*60*60*24*30*365L;

如果你在开始时移动你的 365L,那么你会得到正确的结果:-

if you move your 365L at the start, then you will get the correct result: -

long thirtyYearWithL = 365L*1000*60*60*24*30; // will give you correct result

因为,现在您的 temporary 结果将是 long 类型,并且能够保存该值.

Because, now your temporary result will be of type long, and is capable of holding that value.

这篇关于为什么这两个乘法运算会给出不同的结果?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆