Skip to content

Commit b55d12e

Browse files
thomasjpfanqinhanmin2014
authored andcommitted
FIX Fixes duck typing in VotingClassifier (#14287)
1 parent f7e082d commit b55d12e

File tree

3 files changed

+16
-8
lines changed

3 files changed

+16
-8
lines changed

doc/whats_new/v0.22.rst

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -69,15 +69,18 @@ Changelog
6969
:mod:`sklearn.ensemble`
7070
.......................
7171

72+
- |Feature| :class:`ensemble.HistGradientBoostingClassifier` and
73+
:class:`ensemble.HistGradientBoostingRegressor` have an additional
74+
parameter called `warm_start` that enables warm starting. :pr:`14012` by
75+
:user:`Johann Faouzi <johannfaouzi>`.
76+
7277
- |Fix| :class:`ensemble.HistGradientBoostingClassifier` and
7378
:class:`ensemble.HistGradientBoostingRegressor` now bin the training and
7479
validation data separately to avoid any data leak. :pr:`13933` by
7580
`Nicolas Hug`_.
7681

77-
- |Feature| :class:`ensemble.HistGradientBoostingClassifier` and
78-
:class:`ensemble.HistGradientBoostingRegressor` have an additional
79-
parameter called `warm_start` that enables warm starting. :pr:`14012` by
80-
:user:`Johann Faouzi <johannfaouzi>`.
82+
- |Fix| :func:`ensemble.VotingClassifier.predict_proba` will no longer be
83+
present when `voting='hard'`. :pr:`14287` by `Thomas Fan`_.
8184

8285
- |Enhancement| :class:`ensemble.HistGradientBoostingClassifier` the training
8386
loss or score is now monitored on a class-wise stratified subsample to

sklearn/ensemble/tests/test_voting.py

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,12 @@ def test_predictproba_hardvoting():
6868
('lr2', LogisticRegression())],
6969
voting='hard')
7070
msg = "predict_proba is not available when voting='hard'"
71-
assert_raise_message(AttributeError, msg, eclf.predict_proba, X)
71+
with pytest.raises(AttributeError, match=msg):
72+
eclf.predict_proba
73+
74+
assert not hasattr(eclf, "predict_proba")
75+
eclf.fit(X, y)
76+
assert not hasattr(eclf, "predict_proba")
7277

7378

7479
def test_notfitted():

sklearn/ensemble/voting.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -313,9 +313,6 @@ def _collect_probas(self, X):
313313

314314
def _predict_proba(self, X):
315315
"""Predict class probabilities for X in 'soft' voting """
316-
if self.voting == 'hard':
317-
raise AttributeError("predict_proba is not available when"
318-
" voting=%r" % self.voting)
319316
check_is_fitted(self, 'estimators_')
320317
avg = np.average(self._collect_probas(X), axis=0,
321318
weights=self._weights_not_none)
@@ -335,6 +332,9 @@ def predict_proba(self):
335332
avg : array-like, shape (n_samples, n_classes)
336333
Weighted average probability for each class per sample.
337334
"""
335+
if self.voting == 'hard':
336+
raise AttributeError("predict_proba is not available when"
337+
" voting=%r" % self.voting)
338338
return self._predict_proba
339339

340340
def transform(self, X):

0 commit comments

Comments
 (0)