0

I need to write a function to calculate the (exp(x) - 1) / x, taking into the account the fact that as x approaches 0 the function approaches 1. I have the following implementation

def f(x):
    return np.where(x == 0, 1.0, np.expm1(x) / x)

This is correct in the sense that it returns correct values, but the annoying thing is that when it is called with an x argument that contains zeros, it issues a RuntimeWarning: invalid value encountered in true_divide. I understand that this is because the division by zero actually happens in the third argument of where although those nan values are never used.

Is there a better implementation or a way to avoid the annoying warning?

MikeL
  • 2,369
  • 2
  • 24
  • 38
  • Just ignore the warning? You can silence warnings globally or using a context manage (a `with`) – juanpa.arrivillaga Dec 10 '19 at 11:42
  • How is this ever going to divide by `0`, if you've set the condition to be `x == 0`? – yatu Dec 10 '19 at 11:44
  • 1
    @yatu because it still evaluates `np.expm1(x) / x` – juanpa.arrivillaga Dec 10 '19 at 11:45
  • Use a try-except clause. You should handle the cases where divide by 0 occurs as they can be quite costly. I would not recommend suppressing warnings as it may cause issues if a real issue happens elsewhere. – Jason Chia Dec 10 '19 at 11:45
  • @JasonChia there is no exception to handle here. In any case, you can silence the warnings for just that expression. – juanpa.arrivillaga Dec 10 '19 at 11:45
  • Hmm true, `np.where` does evaluate the whole thing @juanpa – yatu Dec 10 '19 at 11:45
  • @yatu `numpy.where` never gets a chance to do anything else, that is evaluated before it is even passed to `numpy.where`. – juanpa.arrivillaga Dec 10 '19 at 11:46
  • Oooh. Perhaps just a case to check for 0? – Jason Chia Dec 10 '19 at 11:47
  • I'd suggest something like this `np.divide(np.expm1(x), x, out=np.ones_like(x), where=b!=0)` – yatu Dec 10 '19 at 11:48
  • So if x == 0: sub np.expm1(x)/x with Nan – Jason Chia Dec 10 '19 at 11:48
  • Yes gotcha @juanpa , kind of forgot how `np.where` works there – yatu Dec 10 '19 at 11:49
  • 1
    @yatu not to belabor the point, *but it has nothing to do with `numpy.where*, it's a fundamental aspect of how Python works. The only reason I'm trying to be clear is there are some languages where an expression isn't necessarily evaluated when it is passed as an argument. – juanpa.arrivillaga Dec 10 '19 at 11:50
  • @juanpa yes, it makes sense since there's nothing being evaluated here for each value. The whole condition is evaluated in a vectorized manner and the resulting ndarray is filled according to the condition. – yatu Dec 10 '19 at 11:53

0 Answers0