Browse Source
bpo-40290: Add zscore() to statistics.NormalDist. (GH-19547)
pull/19557/head
Raymond Hettinger
6 years ago
committed by
GitHub
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with
37 additions and
0 deletions
-
Doc/library/statistics.rst
-
Lib/statistics.py
-
Lib/test/test_statistics.py
-
Misc/NEWS.d/next/Library/2020-04-15-16-43-48.bpo-40290.eqCMGJ.rst
|
|
|
@ -696,6 +696,16 @@ of applications in statistics. |
|
|
|
Set *n* to 100 for percentiles which gives the 99 cuts points that |
|
|
|
separate the normal distribution into 100 equal sized groups. |
|
|
|
|
|
|
|
.. method:: NormalDist.zscore(x) |
|
|
|
|
|
|
|
Compute the |
|
|
|
`Standard Score <https://www.statisticshowto.com/probability-and-statistics/z-score/>`_ |
|
|
|
describing *x* in terms of the number of standard deviations |
|
|
|
above or below the mean of the normal distribution: |
|
|
|
``(x - mean) / stdev``. |
|
|
|
|
|
|
|
.. versionadded:: 3.9 |
|
|
|
|
|
|
|
Instances of :class:`NormalDist` support addition, subtraction, |
|
|
|
multiplication and division by a constant. These operations |
|
|
|
are used for translation and scaling. For example: |
|
|
|
|
|
|
|
@ -999,6 +999,17 @@ class NormalDist: |
|
|
|
x2 = (a - b) / dv |
|
|
|
return 1.0 - (fabs(Y.cdf(x1) - X.cdf(x1)) + fabs(Y.cdf(x2) - X.cdf(x2))) |
|
|
|
|
|
|
|
def zscore(self, x): |
|
|
|
"""Compute the Standard Score. (x - mean) / stdev |
|
|
|
|
|
|
|
Describes *x* in terms of the number of standard deviations |
|
|
|
above or below the mean of the normal distribution. |
|
|
|
""" |
|
|
|
# https://www.statisticshowto.com/probability-and-statistics/z-score/ |
|
|
|
if not self._sigma: |
|
|
|
raise StatisticsError('zscore() not defined when sigma is zero') |
|
|
|
return (x - self._mu) / self._sigma |
|
|
|
|
|
|
|
@property |
|
|
|
def mean(self): |
|
|
|
"Arithmetic mean of the normal distribution." |
|
|
|
|
|
|
|
@ -2602,6 +2602,21 @@ class TestNormalDist: |
|
|
|
with self.assertRaises(self.module.StatisticsError): |
|
|
|
NormalDist(1, 0).overlap(X) # left operand sigma is zero |
|
|
|
|
|
|
|
def test_zscore(self): |
|
|
|
NormalDist = self.module.NormalDist |
|
|
|
X = NormalDist(100, 15) |
|
|
|
self.assertEqual(X.zscore(142), 2.8) |
|
|
|
self.assertEqual(X.zscore(58), -2.8) |
|
|
|
self.assertEqual(X.zscore(100), 0.0) |
|
|
|
with self.assertRaises(TypeError): |
|
|
|
X.zscore() # too few arguments |
|
|
|
with self.assertRaises(TypeError): |
|
|
|
X.zscore(1, 1) # too may arguments |
|
|
|
with self.assertRaises(TypeError): |
|
|
|
X.zscore(None) # non-numeric type |
|
|
|
with self.assertRaises(self.module.StatisticsError): |
|
|
|
NormalDist(1, 0).zscore(100) # sigma is zero |
|
|
|
|
|
|
|
def test_properties(self): |
|
|
|
X = self.module.NormalDist(100, 15) |
|
|
|
self.assertEqual(X.mean, 100) |
|
|
|
|
|
|
|
@ -0,0 +1 @@ |
|
|
|
Added zscore() to statistics.NormalDist(). |