当前位置: 首页 > 科技观察

在Python中使用KNN算法处理缺失数据

时间:2023-03-20 15:33:33 科技观察

处理缺失数据不是一件容易的事。方法范围从简单的均值插补和完全删除观察到更高级的技术,如MICE。解决问题的挑战在于选择使用哪种方法。今天,我们就来探索一种简单高效的缺失数据填充方法——KNN算法。KNN代表“K最近邻”,这是一种基于定义数量的最近邻进行预测的简单算法。它计算您要分类的实例与训练集中所有其他实例的距离。正如标题所暗示的,我们不会将该算法用于分类目的,而是用于填充缺失值。本文将使用房价数据集,这是一个简单但众所周知的数据集,只有500多个条目。这篇文章的结构如下:数据集加载和探索KNN归因归因优化结论数据集加载和探索如前所述,首先下载房屋数据集。另外,请确保同时导入Numpy和Pandas。这是前几行的样子:默认情况下,数据集的缺失值非常低——单个属性中只有五个:让我们改变它。您通常不会这样做,但我们需要更多缺失值。首先,我们创建两个随机数数组,范围从1到数据集的长度。第一个数组包含35个元素,第二个数组包含20个(任意选择):i1=np.random.choice(a=df.index,size=35)i2=np.random.choice(a=df.index,size=20)这就是第一个数组的样子:你的数组会有所不同,因为随机化过程是随机的。接下来,我们将用NAN替换特定索引处的现有值。方法如下:df.loc[i1,'INDUS']=np.nandf.loc[i2,'TAX']=np.nan现在,让我们再次检查缺失值——这次,计数是different:这是我们从归因开始的所有前期工作。让我们在下一节中这样做。KNN归因整个归因归结为4行代码-其中之一是库导入。我们需要来自sklearn.impute的KNNImputer,然后以众所周知的Scikit-Learn方式创建它的一个实例。这个类需要一个强制参数——n_neighbors。它告诉impersonation参数K的大小是多少。首先,让我们选择3中的任意数字。我们稍后会优化此参数,但3足以启动。接下来,我们可以在计算机上调用fit_transform方法来插补缺失数据。最后,我们将生成的数组转换为pandas.DataFrame对象以便于解释。这是代码:fromsklearn.imputeimportKNNImputerimputer=KNNImputer(n_neighbors=3)imputed=imputer.fit_transform(df)df_imputed=pd.DataFrame(imputed,columns=df.columns)非常简单。现在让我们检查缺失值:仍然存在一个问题——我们如何为K选择正确的值?归因优化该住房数据集旨在通过回归算法进行预测建模,因为目标变量是连续的(MEDV)。这意味着我们可以训练许多预测模型,其中使用不同的K值估算缺失值,并查看哪个模型表现最佳。但首先是进口。我们需要Scikit-Learn提供的一些功能——将数据集拆分为训练和测试子集,训练模型并验证它。我们选择了“随机森林”算法进行训练。RMSE用于验证:fromsklearn.model_selectionimporttrain_test_splitfromsklearn.ensembleimportRandomForestRegressorfromsklearn.metricsimportmean_squared_errorrmse=lambday,yhat:np.sqrt(mean_squared_error(y,yhat))以下是执行优化的必要步骤:迭代K可能范围-1到20都执行使用当前K值进行插补将数据集拆分为训练和测试子集拟合随机森林模型预测测试集使用RMSE进行评估听起来很多,但归结为大约15行代码。这是代码片段:defoptimize_k(data,target):errors=[]forkinrange(1,20,2):imputer=KNNIImputer(n_neighbors=k)imputed=imputer.fit_transform(data)df_imputed=pd.DataFrame(imputed,columns=df.columns)X=df_imputed.drop(target,axis=1)y=df_imputed[目标]X_train,X_test,y_train,y_test=train_test_split(X,y,test_size=0.2,random_state=42)model=RandomForestRegressor()model.fit(X_train,y_train)preds=model.predict(X_test)error=rmse(y_test,preds)errors.append({'K':k,'RMSE':error})returnerrors现在,我们可以使用修改后的(有3列缺失值)调用optimize_k函数,传入目标变量(MEDV):k_errors=optimize_k(data=df,target='MEDV')就这样!k_errors数组看起来像这样:视觉上的意思:看起来K=15是给定范围内的最佳值,因为它导致的错误最小。我们不会涵盖此错误的解释,因为它超出了本文的范围。让我们在下一节中进行总结。总结编写代码来处理缺失数据归因很容易,因为有许多现有的算法我们可以直接使用。但是我们很难理解为什么——理解哪些属性应该被推断,哪些属性不应该被推断。例如,某些值可能会丢失,因为客户没有使用该类型的服务,因此不需要进行估算。最终确定是否需要进行缺失数据处理也需要领域专业知识,咨询领域专家并研究领域是一个很好的方法。