泰坦尼克號之生存預測(2)
- 2019 年 10 月 5 日
- 筆記

泰坦尼克號之生存預測(2)
0.說在前面
1.數據預處理
2.特徵選擇
3.模型選擇
4.結果上傳
5.總結
6.作者的話
0.說在前面
昨天寫了一篇有關leetcode刷題的文章,今天接着上次的kaggle,進行特徵選擇,模型選擇等的一系列步驟。 關於進群交流的夥伴,可以點擊公眾號右下角聯繫我,備註leetcode,進算法群;備註總群,進交流總群!
這裡放上上一節(泰坦尼克號之生存預測(1))的地址:
https://mp.weixin.qq.com/s/7pR1wqPaRl6RGApblJ-fJA
1.數據預處理
【客艙號與生存】
Cabin表示客艙號。
首先我們來對數據缺失值,進行填充。
將缺失值設為NA
X_train['Cabin'] = X_train['Cabin'].fillna('NA') X_test['Cabin'] = X_test['Cabin'].fillna('NA')
其次定義一個方法:
用於獲取客艙號的第一個字母或數字
def Cabin_First_Letter(x): if x == 'NA': return 'NA' return x[0]
將交叉驗證集數據進行上述方法操作
sns.barplot('Cabin_First_Letter', 'Survived', data=X_train.sort_values('Cabin_First_Letter'), ax=axis1)
X_train['Cabin_First_Letter'] = X_train['Cabin'].apply(Cabin_First_Letter) X_test['Cabin_First_Letter'] = X_test['Cabin'].apply(Cabin_First_Letter)
統計客艙號中第一個字母的出現次數:
X_train.groupby('Cabin_First_Letter')['Survived'].count()
結果:
Cabin_First_Letter A 12 B 28 C 41 D 21 E 22 F 8 G 3 NA 488 Name: Survived, dtype: int64
接着,數據處理完了,我們是時候可視化數據,並確定該特徵值與生存的關係!
fig, (axis1,axis2) = plt.subplots(1,2,figsize=(15,5)) sns.barplot('Cabin_First_Letter', 'Survived', data=X_train.sort_values('Cabin_First_Letter'), ax=axis1) sns.barplot('Cabin_First_Letter', 'Survived', data=X_test.sort_values('Cabin_First_Letter'), ax=axis2)

這裡採用seaborn的barplot繪製柱狀圖,圖中的豎線代表誤差棒!圖顯示的是每一個客艙號第一位數字或字母出現的集中分佈趨勢!
針對上述這個圖,我們得出如下結論:
存活率排序:E>D>>B>C>A>.....
然後定義一個方法,進行封裝,依次返回數值!
def Cabin_First_Letter_Code(x): if x == 'E': return 1 if x == 'D': return 2 if x == 'B': return 3 if x == 'C': return 4 if x == 'A': return 5 return 6
然後根據上述的交叉驗證數據集的結果,應用到我們的測試集與訓練集上。
tannike_train['Cabin'] = tannike_train['Cabin'].fillna('NA') tannike_test['Cabin'] = tannike_test['Cabin'].fillna('NA') tannike_train['Cabin_First_Letter'] = tannike_train['Cabin'].apply(Cabin_First_Letter) tannike_test['Cabin_First_Letter'] = tannike_test['Cabin'].apply(Cabin_First_Letter)
由於當前研究的這個數據為等級資料數據,我們這裡用one-hot編碼可有效的處理問題:
tannike_train['Cabin_First_Letter'] = tannike_train['Cabin_First_Letter'].apply(Cabin_First_Letter_Code) tannike_test['Cabin_First_Letter'] = tannike_test['Cabin_First_Letter'].apply(Cabin_First_Letter_Code) tannike_train = pd.get_dummies(columns = ['Cabin_First_Letter'], data = tannike_train) tannike_test = pd.get_dummies(columns = ['Cabin_First_Letter'], data = tannike_test)
【登陸港口與生存】
由於登錄港口數據已經在前一節的缺失值處理掉了,這裡便可以直接對交叉驗證集數據可視化:
fig, (axis1,axis2) = plt.subplots(1,2,figsize=(15,5)) sns.barplot('Embarked', 'Survived', data=X_train.sort_values('Embarked'), ax=axis1) sns.barplot('Embarked', 'Survived', data=X_test.sort_values('Embarked'), ax=axis2)

然後我們對其進行生存排序:
C>Q>S
由於只有三類,直接對訓練集與測試集進行one-hot編碼即可!
tannike_train = pd.get_dummies(tannike_train,columns = ['Embarked']) tannike_test = pd.get_dummies(tannike_test,columns = ['Embarked'])
Pclass 客艙等級(1/2/3等艙位) 同Embarked操作,這個就不闡述了!
【兄弟姐妹與生存】
SibSp 兄弟姐妹數或配偶數
Parch 父母數或子女數
將其與Parch 合併處理!
X_train['Fam_Size'] = X_train['SibSp'] + X_train['Parch'] X_test['Fam_Size'] = X_test['SibSp'] + X_test['Parch']
可視化:
fig, (axis1,axis2) = plt.subplots(1,2,figsize=(15,5)) sns.barplot('Fam_Size', 'Survived', data=X_train.sort_values('Parch'), ax=axis1) sns.barplot('Fam_Size', 'Survived', data=X_test.sort_values('Parch'), ax=axis2)

特徵處理:
分為三類:Solo,Nuclear,Big,並對訓練集與測試集進行one-hot編碼!
import numpy as np def Family_feature(train, test): for i in [train, test]: i['Fam_Size'] = np.where((i['SibSp']+i['Parch']) == 0 , 'Solo', np.where((i['SibSp']+i['Parch']) <= 3,'Nuclear', 'Big')) del i['SibSp'] del i['Parch'] return train, test tannike_train, tannike_test = Family_feature(tannike_train, tannike_test) tannike_train = pd.get_dummies(tannike_train,columns = ['Fam_Size']) tannike_test = pd.get_dummies(tannike_test,columns = ['Fam_Size'])
Fare同理操作!
2.特徵選擇
這裡以全集特徵訓練!刪除某一特徵訓練結果測試,後續~~
X_train_ = tannike_train.loc[X_train.index] X_test_ = tannike_train.loc[X_test.index] Y_train_ = label.loc[X_train.index] Y_test_ = label.loc[X_test.index] X_test_.head(3) X_test_ = X_test_[X_train_.columns] X_test_.head(3) tannike_test = tannike_test[tannike_train.columns] tannike_test.head()
3.模型選擇
【xgboost】
這裡選用xgboost進行測試,下面是選擇的最優情況的代碼,線下測試:0.8097014925373134,線上測試0.80621!
import xgboost as xgb from sklearn.preprocessing import LabelEncoder gbm = xgb.XGBClassifier(max_depth=3, n_estimators=300, learning_rate=0.06,scoring='r3', cv=10, verbose=1, n_jobs=4,) gbm.fit(X_train_, Y_train_) gbm.score(X_test_,Y_test_)
【隨機森林】
線下測試:0.8022388059701493,線上測試0.80621!
rf_ = RandomForestClassifier(random_state = 10, warm_start = True, n_estimators = 900, max_depth = 6, max_features = 'sqrt',min_samples_leaf=1) rf_.fit(X_train_, Y_train_) rf_.score(X_test_,Y_test_)
4.結果上傳
首先通過上述建立的模型進行預測,並輸出到上傳文件中,然後再上傳 !
s = pd.read_csv('./gender_submission.csv') predictions = p.predict(tannike_test) # p為模型分類器 submission = pd.DataFrame({"PassengerId": s.PassengerId, "Survived": predictions.astype(np.int32)}) submission.to_csv("submission-pipe.csv", index=False)

5.總結
- 泰坦尼克號數據大多屬於等級資料,需要用one-hot編碼;
- 特徵選擇,加權的重要性;
- 交叉驗證集構建;
- 多模型選擇與模型融合;
- 當前這個模型單一,特徵提取沒有進行逐一刪選,後續~~
學習參考
https://www.kesci.com/home/project/5af18c294b7639369e6c289c