1

The code gives an error because the value of "var" is very close to zero, less than 1e-80. I tried to fix this error using "Import decimal *", but it didn't really work. Is there a way to tell Python to round a number to zero when float number is very close to zero, i.e. < 1e-50? Or any other way to fix this issue?
Thank you
CODE:

import math
H=6.6260755e-27
K=1.3807e-16
C=2.9979E+10
T=100.0
x=3.07175e-05

cst=2.0*H*H*(C**3.0)/(K*T*T*(x**6.0))
a=H*C/(K*T*x)
var=cst*math.exp(a)/((math.exp(a)-1.0)**2.0)
print var

OUTPUT:

Traceback (most recent call last):
  File "test.py", line 11, in <module>
  var=cst*math.exp(a)/((math.exp(a)-1.0)**2.0)
OverflowError: (34, 'Numerical result out of range')

To Kevin: The code was edited with following lines:

from decimal import *
getcontext().prec = 7
cst=Decimal(2.0*H*H*(C**3.0)/(K*T*T*(x**6.0)))
a=Decimal(H*C/(K*T*x))
8
  • 2
    "I tried to fix this error using "Import decimal *", but it didn't really work." Why not? Let's see the code where you tried it. Commented Aug 3, 2015 at 16:59
  • 2
    "Is there a way to tell Python to round a number to zero when float number is very close to zero, i.e. < 1e-50?" - num = 0 if abs(num - 0) < 1e-50 else num? Commented Aug 3, 2015 at 17:03
  • @jonrsharpe: program needs to compute "var" first in order to use "if" statement. Commented Aug 3, 2015 at 17:15
  • 1
    True, but the code itself does seem to use the syntactically correct from decimal import * Commented Aug 3, 2015 at 17:20
  • 2
    import decimal * isn't a nonsense statement because the decimal module doesn't exist (it does), it's a nonsense statement because it's a SyntaxError. As noted, the correct syntax is from decimal import *. Commented Aug 3, 2015 at 17:29

2 Answers 2

1

The problem is that (math.exp(a)-1.0)**2.0 is too large to hold as an intermediate result.

>>> (math.exp(a) - 1.0)**2.0
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
OverflowError: (34, 'Result too large')

However, for the value of a you are using,

>>> math.exp(a)/(math.exp(a)-1.0) == 1.0
True

so you can essentially cancel that part of the fraction, leaving

var = cst/(math.exp(a)-1.0)

which evaluates nicely to

>>> cst/(math.exp(a)-1.0)
7.932672271698049e-186

If you aren't comfortable rewriting the formula to that extent, use the associativity of the operations to avoid the large intermediate value. The resulting product is the same.

>>> cst/(math.exp(a)-1.0)*math.exp(a)/(math.exp(a)-1.0)
7.932672271698049e-186
Sign up to request clarification or add additional context in comments.

Comments

0

I solved this issue but that will work only for this particular problem, not in general. The main issue is the nature of this function:

math.exp(a)/(math.exp(a)-1.0)**2.0

which decays very rapidly. Problem can be easily solved restricting the value of "a" (which won't make any significant change in calculation). i.e.

if a>200:
    var=0.0
else:
    var=cst*math.exp(a)/((math.exp(a)-1.0)**2.0)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.