Alternative Methods Of Initializing Floats To '+inf', '-inf' And 'nan'
Solution 1:
Technically, yes, there are other ways of initializing such values, but they're all either less obvious, or much less convenient.
If your platform uses IEEE floating point, any float
arithmetic that overflows, without raising any other flags besides overflow, is guaranteed to give you inf
. This means 1.0 / 0.0
probably won't work (Python will detect that this is a division by zero), but the even simpler 1e500
will.
Once you have inf
, you can just do -inf
and inf/inf
to get the negative infinity and NaN values.
But would someone reading your code understand 1e500 / 1e500
as readily as float('nan')
? Probably not.
Meanwhile, you can always do something like struct.unpack('>f', b'\x7f\x80\0\0')[0]
, which unpacks the well-defined bit pattern for an IEEE big-endian double inf
value as a float
, whether your float
is that type under the covers or not. But why would you want to write (or read) that?
But, if you're using Python 3.5 or later, you don't need to initialize those values; you can just use the constants in the math
module:
print(math.inf, +math.inf, -math.inf, math.nan)
And if you're using Python 2.7 or 3.4 or something, you can always just define your own constants and use them over and over:
inf, nan = float('inf'), float('nan')
print(inf, +inf, -inf, nan)
1. Technically, Python doesn't require IEEE floating point. In fact, what it requires are something that acts like the platform's C double
—which C doesn't require to be an IEEE type, and only if that makes sense for the implementation (e.g., Jython is obviously going to use the relevant Java type without caring what the C compiler used to compile the JVM thinks), and it doesn't clarify exactly what it means to act like a C double. However, the float
type—not to mention things like the math
module—really isn't going to work unless float
is something reasonably close to an IEEE float type, like maybe the pre-IEEE IBM and Intel types or the not-quite-IEEE Motorola compat types. Also, as of 2018, the only supported platforms by any of the three existing Python 3.x implementations all give you either IEEE 754-1985 double
or IEEE 754-2008 float64
. But, if this is really a potential issue for your code, you should check sys.float_info
to verify whatever assumptions are relevant.
2. It's conceivable that some platform might use an IEEE 754-1985 long double
or an IEEE 754-2008 float128
or something. If you're worried about that, just use a bigger number. Or, say, 1e500 ** 1e500 ** 1e500
.
3. Well, if you specifically need a quiet or signaling NaN, or one with a custom bit pattern instead of the default one… but anyone who needs that presumably already knows they need that.
Solution 2:
You can access those mathematical constants from the math
module:
>>>from math import inf, nan>>>inf
inf
>>>nan
nan
>>>inf == float('inf')
True
Behind the scenes, in the CPython inplementation, math.inf
and math.nan
are generated using the same technique as that which float('inf')
and float('nan')
use; both approaches invoke the API functions _Py_dg_infinity
and _Py_dg_stdnan
respectively.
Solution 3:
Not sure if this is what you want, but numpy has variables built in for that.
import numpy as npa= np.infb= -np.infc= np.nan
print(a, b, c)
[inf, -inf, nan]
Solution 4:
math.inf
constant was introduced in python3.5, you can read more about in https://docs.python.org/3/library/math.html#constants:
math.inf A floating-point positive infinity. (For negative infinity, use -math.inf.) Equivalent to the output of float('inf').
New in version 3.5.
As you can see below, they're both identical ones:
>>>import math>>>math.inf == float('inf')
True
>>>math.isinf(math.inf)
True
>>>
In case you're also interested about how infinity is checked under the curtains you can take a look to the Py_IS_INFINITY macro.
Solution 5:
If you are looking to get these values through mathematical operations:
import numpy as npa= np.array([-1,0,1],dtype='int8')
a/0
Output:
array([-inf, nan, inf])
This result is consistent with the IEEE 754 floating point behavior.
In IEEE 754 arithmetic, a ÷ +0 is positive infinity when a is positive, negative infinity when a is negative, and NaN when a = ±0.
Post a Comment for "Alternative Methods Of Initializing Floats To '+inf', '-inf' And 'nan'"