8000 Remove zero special handling by jagerber48 · Pull Request #317 · lmfit/uncertainties · GitHub
[go: up one dir, main page]
More Web Proxy on the site http://driver.im/
Skip to content

Remove zero special handling #317

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 8 commits into from
May 23, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 14 additions & 2 deletions CHANGES.rst
Original file line number Diff line number Diff line change
Expand Up @@ -7,21 +7,33 @@ Unreleased 4.x
Changes:

- Includes the `main` branch in continuous integration automation.
- [**BREAKING**] Previously when tallying the uncertainty for a `UFloat` object, the
contribution from other `UFloat` objects with `std_dev == 0` were excluded. Now this
special casing for `std_dev == 0` has been removed so that the contribution from all
contributing `UFloat` objects is included. This changes the behavior in certain
corner cases where `UFloat` `f` is derived from `UFloat` `x`, `x` has `x.s == 0`, but
the derivative of `f` with respect to `x` is `NaN`. For example, previously
`(-1)**ufloat(1, 0)` gave `-1.0+/-0`. The justification for this was that the second
`UFloat` with `std_dev` of `0` should be treated like a regular float. Now the same
calculation returns `-1.0+/-nan`. In this case the `UFloat` in the second argument
of the power operator is treated as a degenerate `UFloat`.

Removes:

- [*BREAKING*] Removes certain deprecated `umath` functions and
- [**BREAKING**] Removes certain deprecated `umath` functions and
`AffineScalarFunc`/`UFloat` methods. The following `umath` functions are removed:
`ceil`, `copysign`, `fabs`, `factorial`, `floor`, `fmod`, `frexp`, `ldexp`, `modf`,
`trunc`. The following `AffineScalarFunc`/`UFloat` methods are removed:
`__floordiv__`, `__mod__`, `__abs__`, `__trunc__`, `__lt__`, `__le__`, `__gt__`,
`__ge__`, `__bool__`.
- [*BREAKING*] Previously it was possible for a `UFloat` object to compare equal to a
- [**BREAKING**] Previously it was possible for a `UFloat` object to compare equal to a
`float` object if the `UFloat` `standard_deviation` was zero and the `UFloat`
`nominal_value` was equal to the `float`. Now, when an equality comparison is made
between a `UFloat` object and another object, if the object is not a `UFloat` then
the equality comparison is deferred to this other object. For the specific case of
`float` this means that the equality comparison always returns `False`.
- [**BREAKING**] The `uncertainties` package is generally dropping formal support for
edge cases involving `UFloat` objects with `std_dev == 0`.

Unreleased
----------
Expand Down
10 changes: 0 additions & 10 deletions doc/tech_guide.rst
Original file line number Diff line number Diff line change
Expand Up @@ -197,16 +197,6 @@ This indicates that **the derivative required by linear error
propagation theory is not defined** (a Monte-Carlo calculation of the
resulting random variable is more adapted to this specific case).

However, even in this case where the derivative at the nominal value
is infinite, the :mod:`uncertainties` package **correctly handles
perfectly precise numbers**:

>>> umath.sqrt(ufloat(0, 0))
0.0+/-0

is thus the correct result, despite the fact that the derivative of
the square root is not defined in zero.

.. _math_def_num_uncert:

Mathematical definition of numbers with uncertainties
Expand Down
7 changes: 0 additions & 7 deletions tests/test_power.py
Original file line number Diff line number Diff line change
Expand Up @@ -88,17 +88,10 @@ def test_power_derivatives(first_ufloat, second_ufloat, first_der, second_der):

power_zero_std_dev_result_cases = [
(0, p, 0),
(zero, p, 0),
(float("nan"), zero, 1),
(one, float("nan"), 1),
(p, 0, 1),
(zero, 0, 1),
(-p, 0, 1),
(-10.3, zero, 1),
(0, zero, 1),
(0.3, zero, 1),
(-p, zero, 1),
(zero, zero, 1),
(p, zero, 1),
(one, -3, 1),
(one, -3.1, 1),
Expand Down
24 changes: 4 additions & 20 deletions uncertainties/core.py
Original file line number Diff line number Diff line change
Expand Up @@ -469,26 +469,10 @@ def error_components(self):
object take scalar values (and are not a tuple, like what
math.frexp() returns, for instance).
"""

# Calculation of the variance:
error_components = {}

for variable, derivative in self.derivatives.items():
# print "TYPE", type(variable), type(derivative)

# Individual standard error due to variable:

# 0 is returned even for a NaN derivative (in this case no
# multiplication by the derivative is performed): an exact
# variable obviously leads to no uncertainty in the
# functions that depend on it.
if variable._std_dev == 0:
# !!! Shouldn't the errors always be floats, as a
# convention of this module?
error_components[variable] = 0
else:
error_components[variable] = abs(derivative * variable._std_dev)

error_components = {
variable: abs(derivative * variable._std_dev)
for variable, derivative in self.derivatives.items()
}
return error_components

@property
Expand Down
Loading
0