使用 python 进行五重交叉验证的缺失值插补
Missing values Imputation with five fold cross validation using python
我有一个包含 165 个实例和 49 个特征的数据集,目标为 1 和 0。这个数据集有缺失值,所以我正在尝试使用 KNNimputer 进行五重交叉验证。这是代码:
from numpy import mean
from numpy import std
from pandas import read_csv
from sklearn.ensemble import RandomForestClassifier
from sklearn.impute import SimpleImputer
from sklearn.impute import KNNImputer
from sklearn.model_selection import cross_val_score
from sklearn.model_selection import RepeatedStratifiedKFold
from sklearn.pipeline import Pipeline
from pandas import read_csv
imputer = KNNImputer(n_neighbors=5, weights='uniform', metric='nan_euclidean')
df=read_csv('data.csv', header=None,na_values='?')
data=df.values
ix = [i for i in range(data.shape[1]) if i != 49]
X, y = data[:, ix], data[:, 49]
model = RandomForestClassifier()
pipeline = Pipeline(steps=[('i', imputer), ('m', model)])
cv = RepeatedStratifiedKFold(n_splits=5, n_repeats=1, random_state=1)
scores = cross_val_score(pipeline, X, y, scoring='accuracy', cv=cv, n_jobs=-1)
但这里的问题是我不需要分数。在填充折叠中的缺失值后,我想要数据集(五折或整个数据集),因为我需要在插补之后使用五折进行特征选择,然后进行分类。那么我怎样才能得到插补后的数据集呢?
正如评论中所讨论的,CV 程序在这里没有任何实际帮助。你真正需要的是:
- 拟合您的
KNNImputer
并使用它来转换(推算)您的训练数据
- 使用这个已经安装好的输入器相应地转换你看不见的数据
这样,您的训练数据和测试数据将共享一个共同的估算过程,因此您选择的任何特征选择方法实际上都适用于这两个数据集。
这是一个使用虚拟数据的演示,改编自 documentation 中的示例:
import numpy as np
from sklearn.impute import KNNImputer
X = [[1, 2, np.nan], [3, 4, 3], [np.nan, 6, 5], [8, 8, 7]] # dummy data
imputer = KNNImputer(n_neighbors=2)
X_imp = imputer.fit_transform(X) # fit imputer & transform training dta in 1 step
X_imp
# result:
array([[1. , 2. , 4. ],
[3. , 4. , 3. ],
[5.5, 6. , 5. ],
[8. , 8. , 7. ]])
# new (unseen - test) data with missing values:
# we DON'T fit the imputer again
X_new = np.array([[7, 3, 4], [np.nan, 8, 7]])
X_new_imp = imputer.transform(X_new) # use the imputer already fitted with the training data
X_new_imp
# result:
array([[7. , 3. , 4. ],
[5.5, 8. , 7. ]])
我有一个包含 165 个实例和 49 个特征的数据集,目标为 1 和 0。这个数据集有缺失值,所以我正在尝试使用 KNNimputer 进行五重交叉验证。这是代码:
from numpy import mean
from numpy import std
from pandas import read_csv
from sklearn.ensemble import RandomForestClassifier
from sklearn.impute import SimpleImputer
from sklearn.impute import KNNImputer
from sklearn.model_selection import cross_val_score
from sklearn.model_selection import RepeatedStratifiedKFold
from sklearn.pipeline import Pipeline
from pandas import read_csv
imputer = KNNImputer(n_neighbors=5, weights='uniform', metric='nan_euclidean')
df=read_csv('data.csv', header=None,na_values='?')
data=df.values
ix = [i for i in range(data.shape[1]) if i != 49]
X, y = data[:, ix], data[:, 49]
model = RandomForestClassifier()
pipeline = Pipeline(steps=[('i', imputer), ('m', model)])
cv = RepeatedStratifiedKFold(n_splits=5, n_repeats=1, random_state=1)
scores = cross_val_score(pipeline, X, y, scoring='accuracy', cv=cv, n_jobs=-1)
但这里的问题是我不需要分数。在填充折叠中的缺失值后,我想要数据集(五折或整个数据集),因为我需要在插补之后使用五折进行特征选择,然后进行分类。那么我怎样才能得到插补后的数据集呢?
正如评论中所讨论的,CV 程序在这里没有任何实际帮助。你真正需要的是:
- 拟合您的
KNNImputer
并使用它来转换(推算)您的训练数据 - 使用这个已经安装好的输入器相应地转换你看不见的数据
这样,您的训练数据和测试数据将共享一个共同的估算过程,因此您选择的任何特征选择方法实际上都适用于这两个数据集。
这是一个使用虚拟数据的演示,改编自 documentation 中的示例:
import numpy as np
from sklearn.impute import KNNImputer
X = [[1, 2, np.nan], [3, 4, 3], [np.nan, 6, 5], [8, 8, 7]] # dummy data
imputer = KNNImputer(n_neighbors=2)
X_imp = imputer.fit_transform(X) # fit imputer & transform training dta in 1 step
X_imp
# result:
array([[1. , 2. , 4. ],
[3. , 4. , 3. ],
[5.5, 6. , 5. ],
[8. , 8. , 7. ]])
# new (unseen - test) data with missing values:
# we DON'T fit the imputer again
X_new = np.array([[7, 3, 4], [np.nan, 8, 7]])
X_new_imp = imputer.transform(X_new) # use the imputer already fitted with the training data
X_new_imp
# result:
array([[7. , 3. , 4. ],
[5.5, 8. , 7. ]])