业界 | 如何达到Kaggle竞赛top 2%?这里有一篇特征探索经验帖
本文作者 Abhay Pawar 多次參加 Kaggle 競賽,并在 Instacart Market Basket Analysis 競賽中拿到 top 2% 的名次。他在多年競賽中總結出了一套特征探索和構建更好機器學習模型的標準方式,本文將介紹這套方法。
在數值數據上構建任意監督學習模型的一個重要方面是理解特征。查看模型的部分依賴圖可幫助理解任意特征對模型輸出的影響。
圖源:http://scikit-learn.org/stable/auto_examples/ensemble/plot_partial_dependence.html
但是,部分依賴圖存在一個問題,即它們是使用訓練好的模型創建的。如果我們可以從訓練數據中直接創建部分依賴圖,那么它將幫助我們更好地理解底層數據。事實上,它能夠幫助你做好以下事情:
特征理解
識別帶噪聲的特征
特征工程
特征重要性
特征 debug
泄露檢測和理解
模型監控
為了使其更加易于使用,作者將這些技術封裝進一個 Python 包 featexp 中,本文將介紹如何使用它進行特征探索。本文使用的是 Kaggle Home Credit Default Risk 競賽的應用數據集。該競賽的任務是使用給定數據預測違約者。
featexp:https://github.com/abhayspawar/featexp
1. 特征理解
特征散點圖 vs. 無用的目標
如果依賴變量(目標)是二元的,則散點圖無效,因為所有點要么是 0 要么是 1。對于連續目標來說,數據點太多會造成難以理解目標 vs 特征趨勢。featexp 創建了更好的圖,可幫助解決該問題。我們來試一下!
from featexp import get_univariate_plots# Plots drawn for all features if nothing is passed in feature_list parameter.
get_univariate_plots(data=data_train, target_col='target',
features_list=['DAYS_BIRTH'], bins=10)
DAYS_BIRTH (age) 的特征 vs 目標圖
featexp 為數值特征創建了同等人口數量的 bin(x 軸),然后計算每個 bin 的目標平均值,再繪制出來(如上圖左)。在我們的案例中,目標平均值是違約率。該圖告訴我們年齡越大的客戶違約率越低。這些圖幫助我們理解特征表達的意義,及其對模型的影響。右圖顯示了每個 bin 中客戶的數量。
2. 識別帶噪聲的特征
帶噪聲的特征導致過擬合,識別它們并非易事。在 featexp 中,你可以輸出一個測試集(或者驗證集),對比訓練/測試集中的特征趨勢來確定帶噪聲的特征。
get_univariate_plots(data=data_train, target_col='target', data_test=data_test, features_list=['DAYS_EMPLOYED'])訓練和測試特征趨勢對比。
featexp 計算兩個指標(如上圖所示),來幫助測量噪聲:
趨勢相關度(見測試圖):如果某個特征未體現目標在訓練集和測試集中的同樣趨勢,它會導致過擬合,因為模型會學習一些在測試數據中并不使用的東西。趨勢相關度有助于理解訓練/測試趨勢的相似度,如何利用訓練和測試集的 bin 的平均目標值來計算趨勢相關度。上圖中的特征相關度為 99%,幾乎沒有噪聲。
趨勢變化:趨勢方向中突然和重復的變化可能表明有噪聲。但是,此類趨勢變化也會在 bin 的人口數量與其它特征不同時,導致其違約率無法與其它 bin 進行對比。
下圖中的特征沒有展現同樣的趨勢,因為趨勢相關度為 85%。這兩個指標可用于刪除帶噪聲的特征。
帶噪聲特征示例。
當特征很多且相互關聯時,刪除低趨勢相關度特征的效果很好。它會帶來更少的過擬合,其它相關特征可以避免信息損失。同時需要注意不要刪除太多重要特征,因為這可能導致性能下降。此外,你無法利用特征重要性來判斷特征是否帶噪聲,因為重要的特征也會帶噪聲!
使用不同時間段的測試數據效果更好,因為你可以借此確定特征趨勢是否一直如此。
featexp 中的 get_trend_stats() 函數返回展示趨勢相關度的數據幀,并隨著特征而改變。
from featexp import get_trend_statsstats = get_trend_stats(data=data_train, target_col='target', data_test=data_test)
get_trend_stats() 返回的數據幀。
下面我們就試著刪除數據中低趨勢相關度的特征,然后看結果是否有所改進。
使用趨勢相關度的不同特征選擇的 AUC。
我們可以看到,趨勢相關度閾值越高,排行榜(LB)AUC 越高。不刪除重要的特征進一步將 LB AUC 提高到 0.74。測試 AUC 的變化與 LB AUC 不同,這一點也很有趣。完整代碼詳見 featexp_demo notebook:https://github.com/abhayspawar/featexp/blob/master/featexp_demo.ipynb。
3. 特征工程
通過查看這些圖所獲取的見解可以幫助你創建更好的特征。更好地理解數據將帶來更好的特征工程。此外,它還可以幫助你改善現有特征。下面我們來看另一個特征 EXT_SOURCE_1:
EXT_SOURCE_1 的特征 vs. 目標圖。
具備高 EXT_SOURCE_1 的客戶具備較低的違約率。但是,第一個 bin(違約率約 8%)沒有遵循該特征趨勢(向上升后下降)。它的負值是-99.985,而且人口數量較多。這可能表明這些是特殊的值,因此不遵循特征趨勢。幸運的是,非線性模型在學習該關系方面不會有問題。而對于線性模型(如 logistic 回歸),此類特殊值和空缺值應該采用類似樣本的默認值進行估計,而不是特征平均值。
4. 特征重要性
featexp 還可以幫助衡量特征重要性。DAYS_BIRTH 和 EXT_SOURCE_1 都具備很好的趨勢。但是 EXT_SOURCE_1 的人口數量集中于特殊值 bin,這表明其重要性可能不如 DAYS_BIRTH?;?XGBoost 模型的特征重要性,DAYS_BIRTH 的重要性高于 EXT_SOURCE_1。
5. 特征 debug
查看 featexp 圖可以幫助你捕捉復雜特征工程中的 bug:
零變化特征僅顯示單個 bin。
檢查一下特征的人數分布看起來是否正確。由于存在一些小 bug,我個人經常遭遇上述極端情況。
在看這些圖之前,一定要假設特征趨勢會是什么樣子。如果特征趨勢看起來不像你期望的那樣,可能表示其中存在一些問題。坦率地說,這種假設趨勢的過程使得構建 ML 模型更加有趣!
6 泄露檢測
從目標到特征的數據泄露會導致過擬合。泄露特征具有很高的特征重要性,但很難理解為什么特征會發生泄露。查看下列 featexp 圖可以幫助你理解。
下面的特征在「Null」bin 中違約率為 0%,在其它 bin 中為 100%。很明顯,這是極端的泄露案例。該特征只有在客戶違約時才有價值。根據特征是什么,這可能是因為 bug 或者該特征只為違約者填充(在這種情況下它會下降)。弄清楚特征泄露的原因可以加速 debug。
理解特征為何泄露。
7 模型監控
由于 featexp 計算兩個數據集之間的趨勢相關性,它可以很輕易地用于模型監控。每次模型被重新訓練之后,就可以把新的訓練數據與測試好的訓練數據(通常從第一次構建模型開始訓練數據)進行對比。趨勢相關性能夠幫助你監控特征信息與目標的關系是否發生任何變化。
原文發布時間為: 2018-11-13
本文作者:AI派
本文來自云棲社區合作伙伴“AI派”,了解相關信息可以關注“AI派”。
總結
以上是生活随笔為你收集整理的业界 | 如何达到Kaggle竞赛top 2%?这里有一篇特征探索经验帖的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 面试无忧之Zookeeper总结心得
- 下一篇: sed 和 awk 的一些用法