Python - Java 数学运算给出不同的结果
Python - Java Math operations give different results
我正在 Java 和 Python 中做一些大量的数学运算。总和相同,但结果不同。
python_n1 = int(math.floor(math.pow(int((int(361) * (int(4900 + 4489))) * int(4356)), int(6))))
BigInteger Java_n1 = (x[20].multiply(x[7].add(x[15])).multiply(x[10])).pow(6);
python_simple_sum = 14764352724**6 #or math.pow(14764352724, 6)
BigInteger Java_simple_sum = new BigInteger("14764352724 ").pow(6)
Python 答案 = 10358251994780842724998096890217137953445700726699419360034816
Java 答案 = 10358251994780842575401275783021915748383652186833068257611776
Java 得到正确的结果,但 python 不是。据我所知,我没有使用浮点数。这里有什么问题。
当你这样做时
int(math.pow(14764352724, 6))
你得到一个提升为幂的大数字,但使用浮点方法,即使参数是整数。转换为整数会丢失精度(原始结果为浮点数:1.0358251994780843e+61
)
当你这样做时
14764352724**6
您使用 二元幂 方法仅使用整数乘法得到一个提升为幂的大数。
所以第二个结果是准确的,而第一个不是
>>> int(math.pow(14764352724,6))
10358251994780842724998096890217137953445700726699419360034816 # wrong
>>> 14764352724**6
10358251994780842575401275783021915748383652186833068257611776 # correct
让我们尝试反汇编 **
和 math.pow
函数:
import dis,math
def test(n):
return n ** 3
def test2(n):
return math.pow(n,3)
dis.dis(test)
dis.dis(test2)
输出
4 0 LOAD_FAST 0 (n)
3 LOAD_CONST 1 (3)
6 BINARY_POWER
7 RETURN_VALUE
7 0 LOAD_GLOBAL 0 (math)
3 LOAD_ATTR 1 (pow)
6 LOAD_FAST 0 (n)
9 LOAD_CONST 1 (3)
12 CALL_FUNCTION 2 (2 positional, 0 keyword pair)
15 RETURN_VALUE
如您所见,函数并不等同。 BINARY_POWER
在第一种情况下被调用。此函数有机会准确执行整数乘法当参数为整数时:
BINARY_POWER()
Implements TOS = TOS1 ** TOS
当参数不全是整数时,二进制幂产生与 math.pow
相同的值:
>>> 14764352724**6.0
1.0358251994780843e+61
>>> int(14764352724**6.0)
10358251994780842724998096890217137953445700726699419360034816
注意:可能增加混淆的是内置的 pow
method, which is different from math.pow
(并且在使用 from math import pow
时被后者覆盖),但在使用时等同于 **
运算符没有模参数:
pow(x, y[, z])
Return x to the power y; if z is present, return x to the power y, modulo z (computed more efficiently than pow(x, y) % z). The two-argument form pow(x, y) is equivalent to using the power operator: x**y.
我正在 Java 和 Python 中做一些大量的数学运算。总和相同,但结果不同。
python_n1 = int(math.floor(math.pow(int((int(361) * (int(4900 + 4489))) * int(4356)), int(6))))
BigInteger Java_n1 = (x[20].multiply(x[7].add(x[15])).multiply(x[10])).pow(6);
python_simple_sum = 14764352724**6 #or math.pow(14764352724, 6)
BigInteger Java_simple_sum = new BigInteger("14764352724 ").pow(6)
Python 答案 = 10358251994780842724998096890217137953445700726699419360034816
Java 答案 = 10358251994780842575401275783021915748383652186833068257611776
Java 得到正确的结果,但 python 不是。据我所知,我没有使用浮点数。这里有什么问题。
当你这样做时
int(math.pow(14764352724, 6))
你得到一个提升为幂的大数字,但使用浮点方法,即使参数是整数。转换为整数会丢失精度(原始结果为浮点数:1.0358251994780843e+61
)
当你这样做时
14764352724**6
您使用 二元幂 方法仅使用整数乘法得到一个提升为幂的大数。
所以第二个结果是准确的,而第一个不是
>>> int(math.pow(14764352724,6))
10358251994780842724998096890217137953445700726699419360034816 # wrong
>>> 14764352724**6
10358251994780842575401275783021915748383652186833068257611776 # correct
让我们尝试反汇编 **
和 math.pow
函数:
import dis,math
def test(n):
return n ** 3
def test2(n):
return math.pow(n,3)
dis.dis(test)
dis.dis(test2)
输出
4 0 LOAD_FAST 0 (n)
3 LOAD_CONST 1 (3)
6 BINARY_POWER
7 RETURN_VALUE
7 0 LOAD_GLOBAL 0 (math)
3 LOAD_ATTR 1 (pow)
6 LOAD_FAST 0 (n)
9 LOAD_CONST 1 (3)
12 CALL_FUNCTION 2 (2 positional, 0 keyword pair)
15 RETURN_VALUE
如您所见,函数并不等同。 BINARY_POWER
在第一种情况下被调用。此函数有机会准确执行整数乘法当参数为整数时:
BINARY_POWER()
Implements TOS = TOS1 ** TOS
当参数不全是整数时,二进制幂产生与 math.pow
相同的值:
>>> 14764352724**6.0
1.0358251994780843e+61
>>> int(14764352724**6.0)
10358251994780842724998096890217137953445700726699419360034816
注意:可能增加混淆的是内置的 pow
method, which is different from math.pow
(并且在使用 from math import pow
时被后者覆盖),但在使用时等同于 **
运算符没有模参数:
pow(x, y[, z])
Return x to the power y; if z is present, return x to the power y, modulo z (computed more efficiently than pow(x, y) % z). The two-argument form pow(x, y) is equivalent to using the power operator: x**y.