python 3.4,windows 10,cython 0.21.1
我正在使用cython
将此函数编译为cdef weakchecksum(data):
"""
Generates a weak checksum from an iterable set of bytes.
"""
cdef long a, b, l
a = b = 0
l = len(data)
for i in range(l):
a += data[i]
b += (l - i)*data[i]
return (b << 16) | a, a, b
产生此错误: “OverflowError:Python int太大而无法转换为C long”
我也尝试将它们声明为unsigned longs。我用什么类型来处理非常大的数字?如果它对于c长度太大有任何解决方法吗?
答案 0 :(得分:6)
如果确保计算在c中(例如,声明i为long,并将数据元素放入cdefed变量或在计算之前将其强制转换),则不会出现此错误。但是,您的实际结果可能因平台而异,具体取决于(可能)生成的精确汇编代码以及由此产生的溢出处理。有更好的算法,正如@ cod3monk3y所指出的那样(查看“简单校验和”链接)。
答案 1 :(得分:4)
cython 将 pyx 文件编译为C,因此它依赖于底层的C编译器。
C中整数类型的大小因不同的平台和操作系统而异,C标准并未规定确切的实现。
然而,事实上的实施惯例。
32位和64位的Windows对int
和long
使用4个字节(32位),对long long
使用8个字节(64位)。 Win32和Win64之间的区别是指针的大小(Win32为32位,Win64为64位)。 (请参阅MSDN上的Data Type Ranges]。
Linux使用另一种模式:int
对于linux-32和linux-64都是32位,long long
总是64位。 long
和指针有所不同:linux-32上为32位,linux-64上为64位。
长话短说:如果您需要在不同平台上未更改的整数类型的最大容量,请使用long long
(或unsigned long long
)。
long long
的数据范围为[–9223372036854775808, 9223372036854775807]
。
如果需要具有任意精度的数字,则GMP library - 高精度算术的事实上的标准。 Python有一个名为gmpy2的包装器。