五、实例:在波士顿房价数据集上用随机森林回归填补缺失值
在波士頓房價數據集上用隨機森林回歸填補缺失值
點擊標題即可獲取源代碼和筆記
一、引入
我們從現實中收集的數據,幾乎不可能是完美無缺的,往往都會有一些缺失值。面對缺失值,很多人選擇的方式是直接將含有缺失值的樣本刪除,這是一種有效的方法,但是有時候填補缺失值會比直接丟棄樣本效果更好,即便我們其實并不知道缺失值的真實樣貌。在sklearn中,我們可以使用sklearn.impute.SimpleImputer來輕松地將均值,中值,或者其他最常用的數值填補到數據中。
二、目標
在這個案例中,我們將使用均值,0,和隨機森林回歸來填補缺失值,并驗證四種狀況下的擬合狀況,找出對使用的數據集來說最佳的缺失值填補方法。
1. 導入需要的庫
import numpy as np import pandas as pd import matplotlib.pyplot as plt from sklearn.datasets import load_boston from sklearn.impute import SimpleImputer from sklearn.ensemble import RandomForestRegressor from sklearn.model_selection import cross_val_score2. 以波士頓數據集為例,導入完整的數據集并探索
dataset = load_boston() dataset.data.shape #總共506*13=6578個數據 X_full, y_full = dataset.data, dataset.target n_samples = X_full.shape[0] n_features = X_full.shape[1]3. 為完整數據集放入缺失值
#首先確定我們希望放入的缺失數據的比例,在這里我們假設是50%,那總共就要有3289個數據缺失 rng = np.random.RandomState(0) missing_rate = 0.5 n_missing_samples = int(np.floor(n_samples * n_features * missing_rate)) #np.floor向下取整,返回.0格式的浮點數 #所有數據要隨機遍布在數據集的各行各列當中,而一個缺失的數據會需要一個行索引和一個列索引 #如果能夠創造一個數組,包含3289個分布在0~506中間的行索引,和3289個分布在0~13之間的列索引,那我們就可 以利用索引來為數據中的任意3289個位置賦空值 #然后我們用0,均值和隨機森林來填寫這些缺失值,然后查看回歸的結果如何 missing_features = rng.randint(0,n_features,n_missing_samples) missing_samples = rng.randint(0,n_samples,n_missing_samples) #missing_samples = rng.choice(dataset.data.shape[0],n_missing_samples,replace=False) #我們現在采樣了3289個數據,遠遠超過我們的樣本量506,所以我們使用隨機抽取的函數randint。但如果我們#需要的數據量小于我們的樣本量506,那我們可以采用np.random.choice來抽樣,choice會隨機抽取不重復的隨機數,因此可以幫助我們讓數據更加分散,確保數據不會集中在一些行中 X_missing = X_full.copy() y_missing = y_full.copy() X_missing[missing_samples,missing_features] = np.nan X_missing = pd.DataFrame(X_missing) #轉換成DataFrame是為了后續方便各種操作,numpy對矩陣的運算速度快到拯救人生,但是在索引等功能上卻不如pandas來得好用4. 使用0和均值填補缺失值
#使用均值進行填補 from sklearn.impute import SimpleImputer imp_mean = SimpleImputer(missing_values=np.nan, strategy='mean') X_missing_mean = imp_mean.fit_transform(X_missing) #使用0進行填補 imp_0 = SimpleImputer(missing_values=np.nan, strategy="constant",fill_value=0) X_missing_0 = imp_0.fit_transform(X_missing)5. 使用隨機森林填補缺失值
基本思想:
任何回歸都是從特征矩陣中學習,然后求解連續型標簽y的過程,之所以能夠實現這個過程,是因為回歸算法認為,特征矩陣和標簽之前存在著某種聯系。實際上,標簽和特征是可以相互轉換的,比如說,在一個“用地區,環境,附近學校數量”預測“房價”的問題中,我們既可以用“地區”,“環境”,“附近學校數量”的數據來預測“房價”,也可以反過來,用“環境”,“附近學校數量”和“房價”來預測“地區”。而回歸填補缺失值,正是利用了這種思想。
對于一個有n個特征的數據來說,其中特征T有缺失值,我們就把特征T當作標簽,其他的n-1個特征和原本的標簽組成新的特征矩陣。那對于T來說,它沒有缺失的部分,就是我們的Y_test,這部分數據既有標簽也有特征,而它缺失的部分,只有特征沒有標簽,就是我們需要預測的部分。
1.特征T不缺失的值對應的其他n-1個特征 + 本來的標簽:X_train
2.特征T不缺失的值:Y_train
3.特征T缺失的值對應的其他n-1個特征 + 本來的標簽:X_test
4.特征T缺失的值:未知,我們需要預測的Y_test
這種做法,對于某一個特征大量缺失,其他特征卻很完整的情況,非常適用。
那如果數據中除了特征T之外,其他特征也有缺失值怎么辦?
答案是遍歷所有的特征,從缺失最少的開始進行填補(因為填補缺失最少的特征所需要的準確信息最少)。填補一個特征時,先將其他特征的缺失值用0代替,每完成一次回歸預測,就將預測值放到原本的特征矩陣中,再繼續填補下一個特征。每一次填補完畢,有缺失值的特征會減少一個,所以每次循環后,需要用0來填補的特征就越來越少。當進行到最后一個特征時(這個特征應該是所有特征中缺失值最多的),已經沒有任何的其他特征需要用0來進行填補了,而我們已經使用回歸為其他特征填補了大量有效信息,可以用來填補缺失最多的特征。遍歷所有的特征后,數據就完整,不再有缺失值了。
6. 對填補好的數據進行建模
#對所有數據進行建模,取得MSE結果 X = [X_full,X_missing_mean,X_missing_0,X_missing_reg] mse = [] std = [] for x in X:estimator = RandomForestRegressor(random_state=0, n_estimators=100)scores = cross_val_score(estimator,x,y_full,scoring='neg_mean_squared_error', cv=5).mean()mse.append(scores * -1)7. 用所得結果畫出條形圖
x_labels = ['Full data','Zero Imputation','Mean Imputation','Regressor Imputation'] colors = ['r', 'g', 'b', 'orange'] plt.figure(figsize=(12, 6)) ax = plt.subplot(111) for i in np.arange(len(mse)):ax.barh(i, mse[i],color=colors[i], alpha=0.6, align='center') ax.set_title('Imputation Techniques with Boston Data') ax.set_xlim(left=np.min(mse) * 0.9,right=np.max(mse) * 1.1) ax.set_yticks(np.arange(len(mse))) ax.set_xlabel('MSE') ax.set_yticklabels(x_labels) plt.show()總結
以上是生活随笔為你收集整理的五、实例:在波士顿房价数据集上用随机森林回归填补缺失值的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: python网络爬虫系列(五)——数据提
- 下一篇: ES6(一)——字面量的增强、解构、le