2015-08-14 16 views
9

Avendo usato principalmente python, mi sono rovinato non dovendomi preoccupare di un overflow di interi. Ora che sto usando Numpy, devo preoccuparmene di nuovo. Vorrei numpy per errore nei casi di overflow, ma non sembra funzionare per int64.Get numpy per avvertire sull'overflow di numeri interi

import numpy 
numpy.seterr(all='raise') 
print("{:,}".format(numpy.prod([10]*50))) 
# -5,376,172,055,173,529,600 
print("{:,}".format(numpy.int64(3200000000) * numpy.int64(3200000000))) 
# -8,206,744,073,709,551,616 
print("{:,}".format(numpy.int32(320000) * numpy.int32(320000))) 
# FloatingPointError: overflow encountered in int_scalars -- Finally getting an error! 

ho sempre potuto aggiungere dtype=object per risolvere questi problemi, ma penserei Int64 è abbastanza buono il più delle volte, è solo paura che può fallire in questo modo difficile da rilevare.

Perché seterr funziona solo per int32? Posso farlo funzionare per int64?

L'unica parte dei numpy.seterr documenti che posso trovare che può suggerire motivo per cui questo potrebbe essere il caso è il seguente passo corto:

noti che le operazioni su interi tipi scalari (come int16) sono gestito come virgola mobile e sono interessati da queste impostazioni.

Ma nulla nei documenti data type suggerisce che int32 e int64 sono in qualche modo concettualmente diversi. Non sono sicuro se int64 non è considerato un "tipo scalare intero".

+3

Sembra un insetto insensibile; vedere https://github.com/numpy/numpy/pull/3199. Stranamente, print (numpy.int64 (2 ** 63-1) * numpy.int64 (2)) * fa * genera un'eccezione sul mio sistema (Ubuntu 14.04, Python 2.7.6, numpy 1.8.2), ma il tuo esempio mostra il comportamento bacato. –

risposta

2

In effetti, il comportamento sembra dipendere dalla dimensione del tipo int. Ecco una lista che include il tuo caso e ne aggiunge altri (avendo impostato numpy.seterr(all='raise')).

In [25]: numpy.int(3200000000) * numpy.int(3200000000) 
Out[25]: 10240000000000000000 

In [26]: numpy.int8(3200000000) * numpy.int8(3200000000) 
Out[26]: 0 

In [27]: numpy.int16(3200000000) * numpy.int16(3200000000) 
--------------------------------------------------------------------------- 
FloatingPointError      Traceback (most recent call last) 
<ipython-input-27-a6185c9da0fd> in <module>() 
----> 1 numpy.int16(3200000000) * numpy.int16(3200000000) 

FloatingPointError: overflow encountered in short_scalars 

In [28]: numpy.int32(3200000000) * numpy.int32(3200000000) 
--------------------------------------------------------------------------- 
FloatingPointError      Traceback (most recent call last) 
<ipython-input-28-a3909399b44a> in <module>() 
----> 1 numpy.int32(3200000000) * numpy.int32(3200000000) 

FloatingPointError: overflow encountered in int_scalars 

In [29]: numpy.int64(3200000000) * numpy.int64(3200000000) 
Out[29]: -8206744073709551616 
Problemi correlati