Skip to content

Commit 6f3d825

Browse files
v0.18.3 (#627)
* bump version * make this test more robust
1 parent ca931a6 commit 6f3d825

File tree

5 files changed

+49
-17
lines changed

5 files changed

+49
-17
lines changed

CHANGELOG.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
### Changelogs
22

3-
### 0.18.3 (dev)
3+
### 0.18.3
44
- Some performance improvements to parametric univariate models.
55
- Suppressing some irrelevant NumPy and autograd warnings, so lifeline warnings are more noticeable.
66
- Improved some warning and error messages.

docs/conf.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,7 @@
6060
#
6161
# The short X.Y version.
6262

63-
version = "0.18.2"
63+
version = "0.18.3"
6464
# The full version, including dev info
6565
release = version
6666

lifelines/fitters/__init__.py

Lines changed: 23 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,8 @@
44
from functools import wraps
55
import sys
66
import warnings
7-
#pylint: disable=wrong-import-position
7+
8+
# pylint: disable=wrong-import-position
89

910
warnings.simplefilter(action="ignore", category=FutureWarning)
1011
from textwrap import dedent
@@ -238,13 +239,13 @@ def __init__(self, *args, **kwargs):
238239
if "alpha" in self._fitted_parameter_names:
239240
raise NameError("'alpha' in _fitted_parameter_names is a lifelines reserved word. Try 'alpha_' instead.")
240241

241-
def _check_cumulative_hazard_is_monotone_and_positive(self):
242-
test_times = np.linspace(0.01, 100, 15)
242+
def _check_cumulative_hazard_is_monotone_and_positive(self, durations):
243243
class_name = self.__class__.__name__
244244

245-
cumulative_hazard = self._cumulative_hazard(self._initial_values, test_times)
245+
cumulative_hazard = self._cumulative_hazard(self._initial_values, durations)
246246
if not np.all(cumulative_hazard > 0):
247-
raise StatisticalWarning(dedent(
247+
warnings.warn(
248+
dedent(
248249
"""\
249250
Cumulative hazard is not strictly positive. For example, try:
250251
@@ -253,11 +254,17 @@ def _check_cumulative_hazard_is_monotone_and_positive(self):
253254
>>> fitter._cumulative_hazard(fitter._initial_values, test_times)
254255
255256
This may harm convergence, or return nonsensical results.
256-
""".format(class_name)))
257+
""".format(
258+
class_name
259+
)
260+
),
261+
StatisticalWarning,
262+
)
257263

258-
derivative_of_cumulative_hazard = self._hazard(self._initial_values, test_times)
264+
derivative_of_cumulative_hazard = self._hazard(self._initial_values, durations)
259265
if not np.all(derivative_of_cumulative_hazard >= 0):
260-
raise StatisticalWarning(dedent(
266+
warnings.warn(
267+
dedent(
261268
"""\
262269
Cumulative hazard is not strictly non-decreasing. For example, try:
263270
@@ -266,7 +273,12 @@ def _check_cumulative_hazard_is_monotone_and_positive(self):
266273
>>> fitter._hazard(fitter._initial_values, test_times)
267274
268275
This may harm convergence, or return nonsensical results.
269-
""".format(class_name)))
276+
""".format(
277+
class_name
278+
)
279+
),
280+
StatisticalWarning,
281+
)
270282

271283
def _initial_values_from_bounds(self):
272284
for (lb, ub) in self._bounds:
@@ -472,16 +484,15 @@ def fit(
472484
if event_observed is not None:
473485
check_nans_or_infs(event_observed)
474486

475-
self._check_cumulative_hazard_is_monotone_and_positive()
476-
477-
478487
self.durations = np.asarray(durations, dtype=float)
479488
# check for negative or 0 durations - these are not allowed in a weibull model.
480489
if np.any(self.durations <= 0):
481490
raise ValueError(
482491
"This model does not allow for non-positive durations. Suggestion: add a small positive value to zero elements."
483492
)
484493

494+
self._check_cumulative_hazard_is_monotone_and_positive(self.durations)
495+
485496
self.event_observed = (
486497
np.asarray(event_observed, dtype=int) if event_observed is not None else np.ones_like(self.durations)
487498
)

lifelines/version.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
11
# -*- coding: utf-8 -*-
22
from __future__ import unicode_literals
33

4-
__version__ = "0.18.2"
4+
__version__ = "0.18.3"

tests/test_estimation.py

Lines changed: 23 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@
3232
StatisticalWarning,
3333
)
3434

35-
from lifelines.fitters import BaseFitter
35+
from lifelines.fitters import BaseFitter, ParametericUnivariateFitter
3636

3737
from lifelines import (
3838
WeibullFitter,
@@ -180,6 +180,27 @@ def test_parametric_univarite_fitters_can_print_summary(
180180
f.summary
181181
f.print_summary()
182182

183+
def test_warnings_for_problematic_cumulative_hazards(self):
184+
class NegativeFitter(ParametericUnivariateFitter):
185+
186+
_fitted_parameter_names = ["a"]
187+
188+
def _cumulative_hazard(self, params, times):
189+
return params[0] * (times - 0.4)
190+
191+
class DecreasingFitter(ParametericUnivariateFitter):
192+
193+
_fitted_parameter_names = ["a"]
194+
195+
def _cumulative_hazard(self, params, times):
196+
return params[0] * 1 / times
197+
198+
with pytest.warns(StatisticalWarning, match="positive") as w:
199+
NegativeFitter().fit([0.01, 0.5, 10.0, 20.0])
200+
201+
with pytest.warns(StatisticalWarning, match="non-decreasing") as w:
202+
DecreasingFitter().fit([0.01, 0.5, 10.0, 20])
203+
183204

184205
class TestUnivariateFitters:
185206
def test_univarite_fitters_with_survival_function_have_conditional_time_to_(
@@ -451,7 +472,7 @@ def test_lnf_inference(self, lnf):
451472

452473
assert abs(mu - lnf.mu_) < 0.05
453474
assert abs(sigma - lnf.sigma_) < 0.05
454-
assert abs(lnf.median_ - np.percentile(X, 50)) < 0.05
475+
assert abs(lnf.median_/np.percentile(X, 50) - 1) < 0.05
455476

456477
def test_lnf_inference_with_large_sigma(self, lnf):
457478
N = 250000

0 commit comments

Comments
 (0)