From fee2717be6c98e03e828cdf9a1a4efc62fc87d6f Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Thu, 4 Apr 2019 12:03:08 +0200 Subject: [PATCH 01/13] Added the parameter to IterativeImputer that allow to stack MissingIndicator transform into it --- sklearn/impute.py | 20 +++++++++++++++++++- sklearn/tests/test_impute.py | 20 ++++++++++++++++++++ 2 files changed, 39 insertions(+), 1 deletion(-) diff --git a/sklearn/impute.py b/sklearn/impute.py index ea4e8663d0313..ba8847de59e86 100644 --- a/sklearn/impute.py +++ b/sklearn/impute.py @@ -573,7 +573,8 @@ def __init__(self, min_value=None, max_value=None, verbose=0, - random_state=None): + random_state=None, + add_indicator=False): self.estimator = estimator self.missing_values = missing_values @@ -587,6 +588,7 @@ def __init__(self, self.max_value = max_value self.verbose = verbose self.random_state = random_state + self.add_indicator = add_indicator def _impute_one_feature(self, X_filled, @@ -895,6 +897,13 @@ def fit_transform(self, X, y=None): .format(self.tol) ) + if self.add_indicator: + self.indicator_ = MissingIndicator( + missing_values=self.missing_values, features="some-missing", + error_on_new=False) + self.indicator_.fit(X) + X_trans = self.indicator_.transform(X) + if self.estimator is None: from .linear_model import BayesianRidge self._estimator = BayesianRidge() @@ -968,6 +977,9 @@ def fit_transform(self, X, y=None): warnings.warn("[IterativeImputer] Early stopping criterion not" " reached.", ConvergenceWarning) Xt[~mask_missing_values] = X[~mask_missing_values] + + if self.add_indicator: + Xt = np.hstack((Xt, X_trans)) return Xt def transform(self, X): @@ -988,6 +1000,9 @@ def transform(self, X): """ check_is_fitted(self, 'initial_imputer_') + if self.add_indicator: + X_trans = self.indicator_.transform(X) + X, Xt, mask_missing_values = self._initial_imputation(X) if self.n_iter_ == 0 or np.all(mask_missing_values): @@ -1016,6 +1031,9 @@ def transform(self, X): i_rnd += 1 Xt[~mask_missing_values] = X[~mask_missing_values] + + if self.add_indicator: + Xt = np.hstack((Xt, X_trans)) return Xt def fit(self, X, y=None): diff --git a/sklearn/tests/test_impute.py b/sklearn/tests/test_impute.py index 59bbb091afbea..416a1e053af75 100644 --- a/sklearn/tests/test_impute.py +++ b/sklearn/tests/test_impute.py @@ -1119,3 +1119,23 @@ def test_inconsistent_dtype_X_missing_values(imputer_constructor, with pytest.raises(ValueError, match=err_msg): imputer.fit_transform(X) + + +@pytest.mark.parametrize("marker", [np.nan, -1, 0]) +def test_iterative_imputer_add_indicator(marker): + X = np.array([ + [1, marker, marker, 2], + [1, 3, marker, 1], + [marker, marker, marker, marker], + [marker, marker, marker, 3], + ]) + X_true = np.array([ + [1., 3., 2., 0., 1., 0.], + [1., 3., 1., 0., 0., 0.], + [1., 3., 2., 1., 1., 1.], + [1, 3., 3., 1., 1., 0.], + ]) + + imputer = IterativeImputer(missing_values=marker, max_iter=1, add_indicator=True) + X_trans = imputer.fit_transform(X) + assert_allclose(X_trans, X_true) From 4456dc183d8a818d515718bd09d3e3968513fe4a Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Tue, 9 Apr 2019 16:09:55 +0200 Subject: [PATCH 02/13] Improved code and test --- sklearn/impute.py | 27 +++++++++++++++++++-------- sklearn/tests/test_impute.py | 11 ++++++----- 2 files changed, 25 insertions(+), 13 deletions(-) diff --git a/sklearn/impute.py b/sklearn/impute.py index e6a49c145ab2c..945a75ddcf0ef 100644 --- a/sklearn/impute.py +++ b/sklearn/impute.py @@ -538,6 +538,14 @@ class IterativeImputer(BaseEstimator, TransformerMixin): ``sample_posterior`` is True. Use an integer for determinism. See :term:`the Glossary `. + add_indicator : boolean, optional (default=False) + If True, a `MissingIndicator` transform will stack onto output + of the imputer's transform. This allows a predictive estimator + to account for missingness despite imputation. If a feature has no + missing values at fit/train time, the feature won't appear on + the missing indicator even if there are missing values at + transform/test time. + Attributes ---------- initial_imputer_ : object of type :class:`sklearn.impute.SimpleImputer` @@ -558,6 +566,10 @@ class IterativeImputer(BaseEstimator, TransformerMixin): n_features_with_missing_ : int Number of features with missing values. + indicator_ : :class:`sklearn.impute.MissingIndicator` + Indicator used to add binary indicators for missing values. + ``None`` if add_indicator is False. + See also -------- SimpleImputer : Univariate imputation of missing values. @@ -925,11 +937,10 @@ def fit_transform(self, X, y=None): ) if self.add_indicator: - self.indicator_ = MissingIndicator( - missing_values=self.missing_values, features="some-missing", - error_on_new=False) - self.indicator_.fit(X) - X_trans = self.indicator_.transform(X) + self.indicator_ = MissingIndicator(missing_values=self.missing_values) + X_trans_indicator = self.indicator_.fit_transform(X) + else: + self.indicator_ = None if self.estimator is None: from .linear_model import BayesianRidge @@ -1006,7 +1017,7 @@ def fit_transform(self, X, y=None): Xt[~mask_missing_values] = X[~mask_missing_values] if self.add_indicator: - Xt = np.hstack((Xt, X_trans)) + Xt = np.hstack((Xt, X_trans_indicator)) return Xt def transform(self, X): @@ -1028,7 +1039,7 @@ def transform(self, X): check_is_fitted(self, 'initial_imputer_') if self.add_indicator: - X_trans = self.indicator_.transform(X) + X_trans_indicator = self.indicator_.transform(X) X, Xt, mask_missing_values = self._initial_imputation(X) @@ -1060,7 +1071,7 @@ def transform(self, X): Xt[~mask_missing_values] = X[~mask_missing_values] if self.add_indicator: - Xt = np.hstack((Xt, X_trans)) + Xt = np.hstack((Xt, X_trans_indicator)) return Xt def fit(self, X, y=None): diff --git a/sklearn/tests/test_impute.py b/sklearn/tests/test_impute.py index 4530009d53d98..759967ec270cb 100644 --- a/sklearn/tests/test_impute.py +++ b/sklearn/tests/test_impute.py @@ -1197,7 +1197,8 @@ def test_imputation_add_indicator_sparse_matrix(arr_type): assert_allclose(X_trans.toarray(), X_true) -@pytest.mark.parametrize("marker", [np.nan, -1, 0]) +# @pytest.mark.parametrize("marker", [np.nan, -1, 0]) +@pytest.mark.parametrize("marker", [np.nan]) def test_iterative_imputer_add_indicator(marker): X = np.array([ [1, marker, marker, 2], @@ -1206,10 +1207,10 @@ def test_iterative_imputer_add_indicator(marker): [marker, marker, marker, 3], ]) X_true = np.array([ - [1., 3., 2., 0., 1., 0.], - [1., 3., 1., 0., 0., 0.], - [1., 3., 2., 1., 1., 1.], - [1, 3., 3., 1., 1., 0.], + [1., 3., 2., 0., 1., 1., 0.], + [1., 3., 1., 0., 0., 1., 0.], + [1., 3., 2., 1., 1., 1., 1.], + [1, 3., 3., 1., 1., 1., 0.], ]) imputer = IterativeImputer(missing_values=marker, max_iter=1, add_indicator=True) From 5d43bc585e54b1ff2ee7d8946e4a856a8d226aa2 Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Tue, 9 Apr 2019 16:10:36 +0200 Subject: [PATCH 03/13] Adjusted docs according to the new feature --- doc/modules/impute.rst | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/doc/modules/impute.rst b/doc/modules/impute.rst index fa8ee3bd4574b..656239f2dfa65 100644 --- a/doc/modules/impute.rst +++ b/doc/modules/impute.rst @@ -109,10 +109,11 @@ imputation round are returned. >>> from sklearn.impute import IterativeImputer >>> imp = IterativeImputer(max_iter=10, random_state=0) >>> imp.fit([[1, 2], [3, 6], [4, 8], [np.nan, 3], [7, np.nan]]) # doctest: +NORMALIZE_WHITESPACE - IterativeImputer(estimator=None, imputation_order='ascending', - initial_strategy='mean', max_iter=10, max_value=None, - min_value=None, missing_values=nan, n_nearest_features=None, - random_state=0, sample_posterior=False, tol=0.001, verbose=0) + IterativeImputer(add_indicator=False, estimator=None, + imputation_order='ascending', initial_strategy='mean', + max_iter=10, max_value=None, min_value=None, + missing_values=nan, n_nearest_features=None, + random_state=0, sample_posterior=False, tol=0.001, verbose=0) >>> X_test = [[np.nan, 2], [6, np.nan], [np.nan, 6]] >>> # the model learns that the second feature is double the first >>> print(np.round(imp.transform(X_test))) From 24c5eef32ff90c743f5d18e624d33a6fb43eda00 Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Tue, 9 Apr 2019 16:39:47 +0200 Subject: [PATCH 04/13] Fixed linter issues --- sklearn/impute.py | 3 ++- sklearn/tests/test_impute.py | 7 ++++--- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/sklearn/impute.py b/sklearn/impute.py index 945a75ddcf0ef..8bbf1bb94e242 100644 --- a/sklearn/impute.py +++ b/sklearn/impute.py @@ -937,7 +937,8 @@ def fit_transform(self, X, y=None): ) if self.add_indicator: - self.indicator_ = MissingIndicator(missing_values=self.missing_values) + self.indicator_ = MissingIndicator( + missing_values=self.missing_values) X_trans_indicator = self.indicator_.fit_transform(X) else: self.indicator_ = None diff --git a/sklearn/tests/test_impute.py b/sklearn/tests/test_impute.py index 759967ec270cb..cf2aa6e07a1f2 100644 --- a/sklearn/tests/test_impute.py +++ b/sklearn/tests/test_impute.py @@ -1197,8 +1197,7 @@ def test_imputation_add_indicator_sparse_matrix(arr_type): assert_allclose(X_trans.toarray(), X_true) -# @pytest.mark.parametrize("marker", [np.nan, -1, 0]) -@pytest.mark.parametrize("marker", [np.nan]) +@pytest.mark.parametrize("marker", [np.nan, -1, 0]) def test_iterative_imputer_add_indicator(marker): X = np.array([ [1, marker, marker, 2], @@ -1213,6 +1212,8 @@ def test_iterative_imputer_add_indicator(marker): [1, 3., 3., 1., 1., 1., 0.], ]) - imputer = IterativeImputer(missing_values=marker, max_iter=1, add_indicator=True) + imputer = IterativeImputer(missing_values=marker, + max_iter=1, + add_indicator=True) X_trans = imputer.fit_transform(X) assert_allclose(X_trans, X_true) From 9023f3e03ecfdc55096d59a71c83a20270210d7b Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Wed, 10 Apr 2019 16:56:32 +0200 Subject: [PATCH 05/13] Improved test coverage --- sklearn/tests/test_impute.py | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/sklearn/tests/test_impute.py b/sklearn/tests/test_impute.py index cf2aa6e07a1f2..2dd011897f299 100644 --- a/sklearn/tests/test_impute.py +++ b/sklearn/tests/test_impute.py @@ -1215,5 +1215,15 @@ def test_iterative_imputer_add_indicator(marker): imputer = IterativeImputer(missing_values=marker, max_iter=1, add_indicator=True) - X_trans = imputer.fit_transform(X) + X_trans = imputer.fit(X).transform(X) assert_allclose(X_trans, X_true) + + +@pytest.mark.parametrize("imputer_constructor", [SimpleImputer, IterativeImputer]) +def test_imputer_without_indicator(imputer_constructor): + X = np.array([[1, 1], + [1, 1]]) + imputer = imputer_constructor() + imputer.fit(X) + + assert imputer.indicator_ is None From 3acc4ac59af4ccc49e43c41904756db67f1076b8 Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Wed, 10 Apr 2019 17:39:38 +0200 Subject: [PATCH 06/13] Fixed linter --- sklearn/tests/test_impute.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/sklearn/tests/test_impute.py b/sklearn/tests/test_impute.py index 2dd011897f299..6d99287c30583 100644 --- a/sklearn/tests/test_impute.py +++ b/sklearn/tests/test_impute.py @@ -1219,7 +1219,8 @@ def test_iterative_imputer_add_indicator(marker): assert_allclose(X_trans, X_true) -@pytest.mark.parametrize("imputer_constructor", [SimpleImputer, IterativeImputer]) +@pytest.mark.parametrize("imputer_constructor", + [SimpleImputer, IterativeImputer]) def test_imputer_without_indicator(imputer_constructor): X = np.array([[1, 1], [1, 1]]) From 90d97a0d77c511a7e65dafd95e73e22b4e8c55f6 Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Fri, 12 Apr 2019 20:45:12 +0200 Subject: [PATCH 07/13] Improved the tests --- sklearn/tests/test_impute.py | 72 +++++++++++++----------------------- 1 file changed, 26 insertions(+), 46 deletions(-) diff --git a/sklearn/tests/test_impute.py b/sklearn/tests/test_impute.py index 6d99287c30583..68cfc27b2346d 100644 --- a/sklearn/tests/test_impute.py +++ b/sklearn/tests/test_impute.py @@ -1147,27 +1147,40 @@ def test_missing_indicator_sparse_no_explicit_zeros(): @pytest.mark.parametrize("marker", [np.nan, -1, 0]) -def test_imputation_add_indicator(marker): +@pytest.mark.parametrize("imputer_constructor", + [SimpleImputer, IterativeImputer]) +def test_imputers_add_indicator(marker, imputer_constructor): X = np.array([ - [marker, 1, 5, marker, 1], - [2, marker, 1, marker, 2], - [6, 3, marker, marker, 3], - [1, 2, 9, marker, 4] + [1, marker, marker, 2], + [1, 3, marker, 1], + [marker, marker, marker, marker], + [marker, marker, marker, 3], ]) X_true = np.array([ - [3., 1., 5., 1., 1., 0., 0., 1.], - [2., 2., 1., 2., 0., 1., 0., 1.], - [6., 3., 5., 3., 0., 0., 1., 1.], - [1., 2., 9., 4., 0., 0., 0., 1.] + [1., 3., 2., 0., 1., 1., 0.], + [1., 3., 1., 0., 0., 1., 0.], + [1., 3., 2., 1., 1., 1., 1.], + [1, 3., 3., 1., 1., 1., 0.], ]) + imputer = imputer_constructor(missing_values=marker, + add_indicator=True) - imputer = SimpleImputer(missing_values=marker, add_indicator=True) - X_trans = imputer.fit_transform(X) - + X_trans = imputer.fit(X).transform(X) assert_allclose(X_trans, X_true) assert_array_equal(imputer.indicator_.features_, np.array([0, 1, 2, 3])) +@pytest.mark.parametrize("imputer_constructor", + [SimpleImputer, IterativeImputer]) +def test_imputer_without_indicator(imputer_constructor): + X = np.array([[1, 1], + [1, 1]]) + imputer = imputer_constructor() + imputer.fit(X) + + assert imputer.indicator_ is None + + @pytest.mark.parametrize( "arr_type", [ @@ -1175,7 +1188,7 @@ def test_imputation_add_indicator(marker): sparse.lil_matrix, sparse.bsr_matrix ] ) -def test_imputation_add_indicator_sparse_matrix(arr_type): +def test_simple_imputation_add_indicator_sparse_matrix(arr_type): X_sparse = arr_type([ [np.nan, 1, 5], [2, np.nan, 1], @@ -1195,36 +1208,3 @@ def test_imputation_add_indicator_sparse_matrix(arr_type): assert sparse.issparse(X_trans) assert X_trans.shape == X_true.shape assert_allclose(X_trans.toarray(), X_true) - - -@pytest.mark.parametrize("marker", [np.nan, -1, 0]) -def test_iterative_imputer_add_indicator(marker): - X = np.array([ - [1, marker, marker, 2], - [1, 3, marker, 1], - [marker, marker, marker, marker], - [marker, marker, marker, 3], - ]) - X_true = np.array([ - [1., 3., 2., 0., 1., 1., 0.], - [1., 3., 1., 0., 0., 1., 0.], - [1., 3., 2., 1., 1., 1., 1.], - [1, 3., 3., 1., 1., 1., 0.], - ]) - - imputer = IterativeImputer(missing_values=marker, - max_iter=1, - add_indicator=True) - X_trans = imputer.fit(X).transform(X) - assert_allclose(X_trans, X_true) - - -@pytest.mark.parametrize("imputer_constructor", - [SimpleImputer, IterativeImputer]) -def test_imputer_without_indicator(imputer_constructor): - X = np.array([[1, 1], - [1, 1]]) - imputer = imputer_constructor() - imputer.fit(X) - - assert imputer.indicator_ is None From 9de8e4a6d021053a8ea91663996aa03e59b073f3 Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Fri, 12 Apr 2019 20:45:38 +0200 Subject: [PATCH 08/13] Updated whats new --- doc/whats_new/v0.21.rst | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/doc/whats_new/v0.21.rst b/doc/whats_new/v0.21.rst index b2df99d9a131b..97647068bf82d 100644 --- a/doc/whats_new/v0.21.rst +++ b/doc/whats_new/v0.21.rst @@ -255,11 +255,11 @@ Support for Python 3.4 and below has been officially dropped. used to be kept if there were no missing values at all. :issue:`13562` by :user:`Jérémie du Boisberranger `. -- |Feature| The :class:`impute.SimpleImputer` has a new parameter - ``'add_indicator'``, which simply stacks a :class:`impute.MissingIndicator` - transform into the output of the imputer's transform. That allows a predictive - estimator to account for missingness. :issue:`12583` by - :user:`Danylo Baibak `. +- |Feature| The :class:`impute.SimpleImputer` and :class:`IterativeImputer` has + a new parameter ``'add_indicator'``, which simply stacks a + :class:`impute.MissingIndicator` transform into the output of the imputer's + transform. That allows a predictive estimator to account for missingness. + :issue:`12583`, `13601` by :user:`Danylo Baibak `. :mod:`sklearn.isotonic` ....................... From 2a01284238c1350d2dc67bbc595359f793154db4 Mon Sep 17 00:00:00 2001 From: Thomas J Fan Date: Sat, 13 Apr 2019 14:56:44 +0200 Subject: [PATCH 09/13] Update doc/whats_new/v0.21.rst Co-Authored-By: DanilBaibak --- doc/whats_new/v0.21.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/whats_new/v0.21.rst b/doc/whats_new/v0.21.rst index 97647068bf82d..1f321896daa6c 100644 --- a/doc/whats_new/v0.21.rst +++ b/doc/whats_new/v0.21.rst @@ -259,7 +259,7 @@ Support for Python 3.4 and below has been officially dropped. a new parameter ``'add_indicator'``, which simply stacks a :class:`impute.MissingIndicator` transform into the output of the imputer's transform. That allows a predictive estimator to account for missingness. - :issue:`12583`, `13601` by :user:`Danylo Baibak `. + :issue:`12583`, :issue:`13601` by :user:`Danylo Baibak `. :mod:`sklearn.isotonic` ....................... From 02908cef39161e4ef6349b252ff03c3fb58676da Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Sat, 13 Apr 2019 18:32:55 +0200 Subject: [PATCH 10/13] Improved the tests for the feature 'add_indicator' --- sklearn/tests/test_impute.py | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/sklearn/tests/test_impute.py b/sklearn/tests/test_impute.py index 68cfc27b2346d..1a3a6447cc284 100644 --- a/sklearn/tests/test_impute.py +++ b/sklearn/tests/test_impute.py @@ -1151,22 +1151,22 @@ def test_missing_indicator_sparse_no_explicit_zeros(): [SimpleImputer, IterativeImputer]) def test_imputers_add_indicator(marker, imputer_constructor): X = np.array([ - [1, marker, marker, 2], - [1, 3, marker, 1], - [marker, marker, marker, marker], - [marker, marker, marker, 3], + [marker, 1, 5, marker, 1], + [2, marker, 1, marker, 2], + [6, 3, marker, marker, 3], + [1, 2, 9, marker, 4] ]) - X_true = np.array([ - [1., 3., 2., 0., 1., 1., 0.], - [1., 3., 1., 0., 0., 1., 0.], - [1., 3., 2., 1., 1., 1., 1.], - [1, 3., 3., 1., 1., 1., 0.], + X_true_indicator = np.array([ + [1., 0., 0., 1.], + [0., 1., 0., 1.], + [0., 0., 1., 1.], + [0., 0., 0., 1.] ]) imputer = imputer_constructor(missing_values=marker, add_indicator=True) X_trans = imputer.fit(X).transform(X) - assert_allclose(X_trans, X_true) + assert_allclose(X_trans[:, -4:], X_true_indicator) assert_array_equal(imputer.indicator_.features_, np.array([0, 1, 2, 3])) From beb57afb8fda182c115c27aead3a82a32072c9ba Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Mon, 15 Apr 2019 09:12:48 +0200 Subject: [PATCH 11/13] Added the comment for the test --- sklearn/tests/test_impute.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/sklearn/tests/test_impute.py b/sklearn/tests/test_impute.py index 1a3a6447cc284..979140ba246cf 100644 --- a/sklearn/tests/test_impute.py +++ b/sklearn/tests/test_impute.py @@ -1166,6 +1166,8 @@ def test_imputers_add_indicator(marker, imputer_constructor): add_indicator=True) X_trans = imputer.fit(X).transform(X) + # The test is for testing the indicator, + # that's why we're looking at the last 4 columns only. assert_allclose(X_trans[:, -4:], X_true_indicator) assert_array_equal(imputer.indicator_.features_, np.array([0, 1, 2, 3])) From 7847afa6464287511cf88e4ff26a8c57a8051304 Mon Sep 17 00:00:00 2001 From: DanilBaibak Date: Mon, 15 Apr 2019 11:51:59 +0200 Subject: [PATCH 12/13] Fixed indentation --- doc/modules/impute.rst | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/doc/modules/impute.rst b/doc/modules/impute.rst index 656239f2dfa65..777a2bd157b29 100644 --- a/doc/modules/impute.rst +++ b/doc/modules/impute.rst @@ -110,10 +110,11 @@ imputation round are returned. >>> imp = IterativeImputer(max_iter=10, random_state=0) >>> imp.fit([[1, 2], [3, 6], [4, 8], [np.nan, 3], [7, np.nan]]) # doctest: +NORMALIZE_WHITESPACE IterativeImputer(add_indicator=False, estimator=None, - imputation_order='ascending', initial_strategy='mean', - max_iter=10, max_value=None, min_value=None, - missing_values=nan, n_nearest_features=None, - random_state=0, sample_posterior=False, tol=0.001, verbose=0) + imputation_order='ascending', initial_strategy='mean', + max_iter=10, max_value=None, min_value=None, + missing_values=nan, n_nearest_features=None, + random_state=0, sample_posterior=False, tol=0.001, + verbose=0) >>> X_test = [[np.nan, 2], [6, np.nan], [np.nan, 6]] >>> # the model learns that the second feature is double the first >>> print(np.round(imp.transform(X_test))) From 4564378cc518e7527dba27ff739c1b0b4201e375 Mon Sep 17 00:00:00 2001 From: Nicolas Hug Date: Mon, 15 Apr 2019 20:58:09 +0200 Subject: [PATCH 13/13] Update doc/whats_new/v0.21.rst Co-Authored-By: DanilBaibak --- doc/whats_new/v0.21.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/whats_new/v0.21.rst b/doc/whats_new/v0.21.rst index 1f321896daa6c..cd760e05d0bbd 100644 --- a/doc/whats_new/v0.21.rst +++ b/doc/whats_new/v0.21.rst @@ -255,7 +255,7 @@ Support for Python 3.4 and below has been officially dropped. used to be kept if there were no missing values at all. :issue:`13562` by :user:`Jérémie du Boisberranger `. -- |Feature| The :class:`impute.SimpleImputer` and :class:`IterativeImputer` has +- |Feature| The :class:`impute.SimpleImputer` and :class:`IterativeImputer` have a new parameter ``'add_indicator'``, which simply stacks a :class:`impute.MissingIndicator` transform into the output of the imputer's transform. That allows a predictive estimator to account for missingness.