Coverage for /var/srv/projects/api.amasfac.comuna18.com/tmp/venv/lib/python3.9/site-packages/numpy/core/_ufunc_config.py: 70%
87 statements
« prev ^ index » next coverage.py v6.4.4, created at 2023-07-17 14:22 -0600
« prev ^ index » next coverage.py v6.4.4, created at 2023-07-17 14:22 -0600
1"""
2Functions for changing global ufunc configuration
4This provides helpers which wrap `umath.geterrobj` and `umath.seterrobj`
5"""
6import collections.abc
7import contextlib
9from .overrides import set_module
10from .umath import (
11 UFUNC_BUFSIZE_DEFAULT,
12 ERR_IGNORE, ERR_WARN, ERR_RAISE, ERR_CALL, ERR_PRINT, ERR_LOG, ERR_DEFAULT,
13 SHIFT_DIVIDEBYZERO, SHIFT_OVERFLOW, SHIFT_UNDERFLOW, SHIFT_INVALID,
14)
15from . import umath
17__all__ = [
18 "seterr", "geterr", "setbufsize", "getbufsize", "seterrcall", "geterrcall",
19 "errstate",
20]
22_errdict = {"ignore": ERR_IGNORE,
23 "warn": ERR_WARN,
24 "raise": ERR_RAISE,
25 "call": ERR_CALL,
26 "print": ERR_PRINT,
27 "log": ERR_LOG}
29_errdict_rev = {value: key for key, value in _errdict.items()}
32@set_module('numpy')
33def seterr(all=None, divide=None, over=None, under=None, invalid=None):
34 """
35 Set how floating-point errors are handled.
37 Note that operations on integer scalar types (such as `int16`) are
38 handled like floating point, and are affected by these settings.
40 Parameters
41 ----------
42 all : {'ignore', 'warn', 'raise', 'call', 'print', 'log'}, optional
43 Set treatment for all types of floating-point errors at once:
45 - ignore: Take no action when the exception occurs.
46 - warn: Print a `RuntimeWarning` (via the Python `warnings` module).
47 - raise: Raise a `FloatingPointError`.
48 - call: Call a function specified using the `seterrcall` function.
49 - print: Print a warning directly to ``stdout``.
50 - log: Record error in a Log object specified by `seterrcall`.
52 The default is not to change the current behavior.
53 divide : {'ignore', 'warn', 'raise', 'call', 'print', 'log'}, optional
54 Treatment for division by zero.
55 over : {'ignore', 'warn', 'raise', 'call', 'print', 'log'}, optional
56 Treatment for floating-point overflow.
57 under : {'ignore', 'warn', 'raise', 'call', 'print', 'log'}, optional
58 Treatment for floating-point underflow.
59 invalid : {'ignore', 'warn', 'raise', 'call', 'print', 'log'}, optional
60 Treatment for invalid floating-point operation.
62 Returns
63 -------
64 old_settings : dict
65 Dictionary containing the old settings.
67 See also
68 --------
69 seterrcall : Set a callback function for the 'call' mode.
70 geterr, geterrcall, errstate
72 Notes
73 -----
74 The floating-point exceptions are defined in the IEEE 754 standard [1]_:
76 - Division by zero: infinite result obtained from finite numbers.
77 - Overflow: result too large to be expressed.
78 - Underflow: result so close to zero that some precision
79 was lost.
80 - Invalid operation: result is not an expressible number, typically
81 indicates that a NaN was produced.
83 .. [1] https://en.wikipedia.org/wiki/IEEE_754
85 Examples
86 --------
87 >>> old_settings = np.seterr(all='ignore') #seterr to known value
88 >>> np.seterr(over='raise')
89 {'divide': 'ignore', 'over': 'ignore', 'under': 'ignore', 'invalid': 'ignore'}
90 >>> np.seterr(**old_settings) # reset to default
91 {'divide': 'ignore', 'over': 'raise', 'under': 'ignore', 'invalid': 'ignore'}
93 >>> np.int16(32000) * np.int16(3)
94 30464
95 >>> old_settings = np.seterr(all='warn', over='raise')
96 >>> np.int16(32000) * np.int16(3)
97 Traceback (most recent call last):
98 File "<stdin>", line 1, in <module>
99 FloatingPointError: overflow encountered in short_scalars
101 >>> old_settings = np.seterr(all='print')
102 >>> np.geterr()
103 {'divide': 'print', 'over': 'print', 'under': 'print', 'invalid': 'print'}
104 >>> np.int16(32000) * np.int16(3)
105 30464
107 """
109 pyvals = umath.geterrobj()
110 old = geterr()
112 if divide is None:
113 divide = all or old['divide']
114 if over is None:
115 over = all or old['over']
116 if under is None:
117 under = all or old['under']
118 if invalid is None:
119 invalid = all or old['invalid']
121 maskvalue = ((_errdict[divide] << SHIFT_DIVIDEBYZERO) +
122 (_errdict[over] << SHIFT_OVERFLOW) +
123 (_errdict[under] << SHIFT_UNDERFLOW) +
124 (_errdict[invalid] << SHIFT_INVALID))
126 pyvals[1] = maskvalue
127 umath.seterrobj(pyvals)
128 return old
131@set_module('numpy')
132def geterr():
133 """
134 Get the current way of handling floating-point errors.
136 Returns
137 -------
138 res : dict
139 A dictionary with keys "divide", "over", "under", and "invalid",
140 whose values are from the strings "ignore", "print", "log", "warn",
141 "raise", and "call". The keys represent possible floating-point
142 exceptions, and the values define how these exceptions are handled.
144 See Also
145 --------
146 geterrcall, seterr, seterrcall
148 Notes
149 -----
150 For complete documentation of the types of floating-point exceptions and
151 treatment options, see `seterr`.
153 Examples
154 --------
155 >>> np.geterr()
156 {'divide': 'warn', 'over': 'warn', 'under': 'ignore', 'invalid': 'warn'}
157 >>> np.arange(3.) / np.arange(3.)
158 array([nan, 1., 1.])
160 >>> oldsettings = np.seterr(all='warn', over='raise')
161 >>> np.geterr()
162 {'divide': 'warn', 'over': 'raise', 'under': 'warn', 'invalid': 'warn'}
163 >>> np.arange(3.) / np.arange(3.)
164 array([nan, 1., 1.])
166 """
167 maskvalue = umath.geterrobj()[1]
168 mask = 7
169 res = {}
170 val = (maskvalue >> SHIFT_DIVIDEBYZERO) & mask
171 res['divide'] = _errdict_rev[val]
172 val = (maskvalue >> SHIFT_OVERFLOW) & mask
173 res['over'] = _errdict_rev[val]
174 val = (maskvalue >> SHIFT_UNDERFLOW) & mask
175 res['under'] = _errdict_rev[val]
176 val = (maskvalue >> SHIFT_INVALID) & mask
177 res['invalid'] = _errdict_rev[val]
178 return res
181@set_module('numpy')
182def setbufsize(size):
183 """
184 Set the size of the buffer used in ufuncs.
186 Parameters
187 ----------
188 size : int
189 Size of buffer.
191 """
192 if size > 10e6:
193 raise ValueError("Buffer size, %s, is too big." % size)
194 if size < 5:
195 raise ValueError("Buffer size, %s, is too small." % size)
196 if size % 16 != 0:
197 raise ValueError("Buffer size, %s, is not a multiple of 16." % size)
199 pyvals = umath.geterrobj()
200 old = getbufsize()
201 pyvals[0] = size
202 umath.seterrobj(pyvals)
203 return old
206@set_module('numpy')
207def getbufsize():
208 """
209 Return the size of the buffer used in ufuncs.
211 Returns
212 -------
213 getbufsize : int
214 Size of ufunc buffer in bytes.
216 """
217 return umath.geterrobj()[0]
220@set_module('numpy')
221def seterrcall(func):
222 """
223 Set the floating-point error callback function or log object.
225 There are two ways to capture floating-point error messages. The first
226 is to set the error-handler to 'call', using `seterr`. Then, set
227 the function to call using this function.
229 The second is to set the error-handler to 'log', using `seterr`.
230 Floating-point errors then trigger a call to the 'write' method of
231 the provided object.
233 Parameters
234 ----------
235 func : callable f(err, flag) or object with write method
236 Function to call upon floating-point errors ('call'-mode) or
237 object whose 'write' method is used to log such message ('log'-mode).
239 The call function takes two arguments. The first is a string describing
240 the type of error (such as "divide by zero", "overflow", "underflow",
241 or "invalid value"), and the second is the status flag. The flag is a
242 byte, whose four least-significant bits indicate the type of error, one
243 of "divide", "over", "under", "invalid"::
245 [0 0 0 0 divide over under invalid]
247 In other words, ``flags = divide + 2*over + 4*under + 8*invalid``.
249 If an object is provided, its write method should take one argument,
250 a string.
252 Returns
253 -------
254 h : callable, log instance or None
255 The old error handler.
257 See Also
258 --------
259 seterr, geterr, geterrcall
261 Examples
262 --------
263 Callback upon error:
265 >>> def err_handler(type, flag):
266 ... print("Floating point error (%s), with flag %s" % (type, flag))
267 ...
269 >>> saved_handler = np.seterrcall(err_handler)
270 >>> save_err = np.seterr(all='call')
272 >>> np.array([1, 2, 3]) / 0.0
273 Floating point error (divide by zero), with flag 1
274 array([inf, inf, inf])
276 >>> np.seterrcall(saved_handler)
277 <function err_handler at 0x...>
278 >>> np.seterr(**save_err)
279 {'divide': 'call', 'over': 'call', 'under': 'call', 'invalid': 'call'}
281 Log error message:
283 >>> class Log:
284 ... def write(self, msg):
285 ... print("LOG: %s" % msg)
286 ...
288 >>> log = Log()
289 >>> saved_handler = np.seterrcall(log)
290 >>> save_err = np.seterr(all='log')
292 >>> np.array([1, 2, 3]) / 0.0
293 LOG: Warning: divide by zero encountered in divide
294 array([inf, inf, inf])
296 >>> np.seterrcall(saved_handler)
297 <numpy.core.numeric.Log object at 0x...>
298 >>> np.seterr(**save_err)
299 {'divide': 'log', 'over': 'log', 'under': 'log', 'invalid': 'log'}
301 """
302 if func is not None and not isinstance(func, collections.abc.Callable):
303 if (not hasattr(func, 'write') or
304 not isinstance(func.write, collections.abc.Callable)):
305 raise ValueError("Only callable can be used as callback")
306 pyvals = umath.geterrobj()
307 old = geterrcall()
308 pyvals[2] = func
309 umath.seterrobj(pyvals)
310 return old
313@set_module('numpy')
314def geterrcall():
315 """
316 Return the current callback function used on floating-point errors.
318 When the error handling for a floating-point error (one of "divide",
319 "over", "under", or "invalid") is set to 'call' or 'log', the function
320 that is called or the log instance that is written to is returned by
321 `geterrcall`. This function or log instance has been set with
322 `seterrcall`.
324 Returns
325 -------
326 errobj : callable, log instance or None
327 The current error handler. If no handler was set through `seterrcall`,
328 ``None`` is returned.
330 See Also
331 --------
332 seterrcall, seterr, geterr
334 Notes
335 -----
336 For complete documentation of the types of floating-point exceptions and
337 treatment options, see `seterr`.
339 Examples
340 --------
341 >>> np.geterrcall() # we did not yet set a handler, returns None
343 >>> oldsettings = np.seterr(all='call')
344 >>> def err_handler(type, flag):
345 ... print("Floating point error (%s), with flag %s" % (type, flag))
346 >>> oldhandler = np.seterrcall(err_handler)
347 >>> np.array([1, 2, 3]) / 0.0
348 Floating point error (divide by zero), with flag 1
349 array([inf, inf, inf])
351 >>> cur_handler = np.geterrcall()
352 >>> cur_handler is err_handler
353 True
355 """
356 return umath.geterrobj()[2]
359class _unspecified:
360 pass
363_Unspecified = _unspecified()
366@set_module('numpy')
367class errstate(contextlib.ContextDecorator):
368 """
369 errstate(**kwargs)
371 Context manager for floating-point error handling.
373 Using an instance of `errstate` as a context manager allows statements in
374 that context to execute with a known error handling behavior. Upon entering
375 the context the error handling is set with `seterr` and `seterrcall`, and
376 upon exiting it is reset to what it was before.
378 .. versionchanged:: 1.17.0
379 `errstate` is also usable as a function decorator, saving
380 a level of indentation if an entire function is wrapped.
381 See :py:class:`contextlib.ContextDecorator` for more information.
383 Parameters
384 ----------
385 kwargs : {divide, over, under, invalid}
386 Keyword arguments. The valid keywords are the possible floating-point
387 exceptions. Each keyword should have a string value that defines the
388 treatment for the particular error. Possible values are
389 {'ignore', 'warn', 'raise', 'call', 'print', 'log'}.
391 See Also
392 --------
393 seterr, geterr, seterrcall, geterrcall
395 Notes
396 -----
397 For complete documentation of the types of floating-point exceptions and
398 treatment options, see `seterr`.
400 Examples
401 --------
402 >>> olderr = np.seterr(all='ignore') # Set error handling to known state.
404 >>> np.arange(3) / 0.
405 array([nan, inf, inf])
406 >>> with np.errstate(divide='warn'):
407 ... np.arange(3) / 0.
408 array([nan, inf, inf])
410 >>> np.sqrt(-1)
411 nan
412 >>> with np.errstate(invalid='raise'):
413 ... np.sqrt(-1)
414 Traceback (most recent call last):
415 File "<stdin>", line 2, in <module>
416 FloatingPointError: invalid value encountered in sqrt
418 Outside the context the error handling behavior has not changed:
420 >>> np.geterr()
421 {'divide': 'ignore', 'over': 'ignore', 'under': 'ignore', 'invalid': 'ignore'}
423 """
425 def __init__(self, *, call=_Unspecified, **kwargs):
426 self.call = call
427 self.kwargs = kwargs
429 def __enter__(self):
430 self.oldstate = seterr(**self.kwargs)
431 if self.call is not _Unspecified: 431 ↛ 432line 431 didn't jump to line 432, because the condition on line 431 was never true
432 self.oldcall = seterrcall(self.call)
434 def __exit__(self, *exc_info):
435 seterr(**self.oldstate)
436 if self.call is not _Unspecified: 436 ↛ 437line 436 didn't jump to line 437, because the condition on line 436 was never true
437 seterrcall(self.oldcall)
440def _setdef():
441 defval = [UFUNC_BUFSIZE_DEFAULT, ERR_DEFAULT, None]
442 umath.seterrobj(defval)
445# set the default values
446_setdef()