機(jī)器學(xué)習(xí)項(xiàng)目流程及模型評估驗(yàn)證

4.9日到現(xiàn)在一直在做Udacity的P1項(xiàng)目——波士頓房價(jià)預(yù)測盛龄。這個(gè)項(xiàng)目讓我收獲最大的就是理清了機(jī)器學(xué)習(xí)解決問題的整體流程斩启,搭起一個(gè)框架序调,學(xué)會了尋找模型的最優(yōu)參數(shù)以及模型的評估和驗(yàn)證方法。

機(jī)器學(xué)習(xí)項(xiàng)目流程思維導(dǎo)圖.JPG

numpy簡單的統(tǒng)計(jì)分析整理

import numpy as np
a = np.array([1,2,3,4,5])
# 最小值
minimum_a = np.min(a)
# 最大值
maximum_a = np.max(a)
# 平均值
mean_a = np.mean(a)
# 中位數(shù)
median_a = np.median(a)
# 標(biāo)準(zhǔn)差
std_a = np.std(a)
# 方差
var_a = np.var(a)
# 和
sum_a = np.sum(a)

pandas讀取處理csv數(shù)據(jù)

目前主要用的就是讀取csv兔簇,然后從表中移除目標(biāo)列发绢,提取特征列。panda讀出來之后是一個(gè)DataFrame垄琐。

data = pd.read_csv('xxx')
outcome = data['XXX'] # outcome是目標(biāo)列
features = data.drop('XXX', axis = 1) # features是移除目標(biāo)列后剩下的特征

模型評估驗(yàn)證

誤差來源

模型誤差常見來源:因模型無法表示基本數(shù)據(jù)的復(fù)雜度造成的偏差(bias)或者因模型對訓(xùn)練它所用的有限數(shù)據(jù)過度敏感造成的方差(Variance)

偏差影響模型的正確性(欠擬合)边酒,方差影響模型的不確定性(過擬合)。
sklearn的學(xué)習(xí)曲線learning_curve可以找到偏差和方差

評估驗(yàn)證

模型的評估驗(yàn)證分兩步狸窘,首先選擇性能指標(biāo)墩朦,然后測試模型表現(xiàn)。機(jī)器學(xué)習(xí)有分類問題和回歸問題兩大類翻擒,這兩類有不同的性能指標(biāo)氓涣,分類問題的指標(biāo)有accuracy、precision陋气、recall劳吠、F1分?jǐn)?shù);回歸問題有誤差指標(biāo)和分?jǐn)?shù)指標(biāo)恩伺,其中誤差指標(biāo)包括平均絕對誤差和均方誤差赴背,分?jǐn)?shù)指標(biāo)包括R2分?jǐn)?shù)和可釋方差分?jǐn)?shù),誤差指標(biāo)越接近0越好晶渠,分?jǐn)?shù)指標(biāo)越接近1越好凰荚。

分類問題

準(zhǔn)確率(accuracy)

在分類中,準(zhǔn)確率被描述為特定類的所有項(xiàng)中正確分類的數(shù)量褒脯。

準(zhǔn)確率 = 正確識別的items數(shù)量 / 所有items數(shù)量

準(zhǔn)確率的缺陷在于不適用于skewed class便瑟,skewed class是指有很多數(shù)據(jù)點(diǎn),大部分屬于一個(gè)類番川,其余的小部分屬于一個(gè)類到涂,比如titanic生還問題脊框,猜測全部死亡,accuracy也不會很低践啄,一些算法算出來可能還不猜測全部死亡準(zhǔn)確率高浇雹,同理猜測全部存活,accuracy就會很低屿讽,可能再怎么進(jìn)行下一步判斷也依然提高不了多少昭灵。
sklearn有專門計(jì)算accuracy的函數(shù):

import numpy as np
from sklearn.metrics import accuracy_score
y_pred = [0,2,1,3]
y_true = [0,1,2,3]
accuracy_score = accuracy_score(y_true, y_pred)
print(accuracy_score) # 0.5
accuracy_score = accuracy_score(y_true, y_pred, normalize=False)
print(accuracy_score) # 2
精確率(precision)

precision = true_positives / (true_positives + false_positives)

精確率就是正確歸為此類的占(正確歸為此類的+誤歸為此類的)百分比。
sklearn有專門計(jì)算precision的函數(shù):

>>> from sklearn.metrics import precision_score
>>> y_true = [0, 1, 2, 0, 1, 2]
>>> y_pred = [0, 2, 1, 0, 0, 1]
>>> precision_score(y_true, y_pred, average='macro')  
0.22...
>>> precision_score(y_true, y_pred, average='micro')  
0.33...
>>> precision_score(y_true, y_pred, average='weighted')
... 
0.22...
>>> precision_score(y_true, y_pred, average=None)  
array([ 0.66...,  0.        ,  0.        ])
召回率(recall)

recall = true_positives / (true_positives + false_negtives)

召回率就是正確歸為此類的占(正確歸為此類的+本來是此類但是沒有歸為此類的)百分比伐谈。
sklearn有專門計(jì)算precision的函數(shù):

>>> from sklearn.metrics import recall_score
>>> y_true = [0, 1, 2, 0, 1, 2]
>>> y_pred = [0, 2, 1, 0, 0, 1]
>>> recall_score(y_true, y_pred, average='macro')  
0.33...
>>> recall_score(y_true, y_pred, average='micro')  
0.33...
>>> recall_score(y_true, y_pred, average='weighted')  
0.33...
>>> recall_score(y_true, y_pred, average=None)
array([ 1.,  0.,  0.])
F1分?jǐn)?shù)

F1 分?jǐn)?shù)會同時(shí)考慮精確率和召回率烂完,以便計(jì)算新的分?jǐn)?shù)∷锌茫可將 F1 分?jǐn)?shù)理解為精確率和召回率的加權(quán)平均值抠蚣,其中 F1 分?jǐn)?shù)的最佳值為 1、最差值為 0:
F1 = 2 x (精確率 x 召回率) / (精確率 + 召回率)

>>> from sklearn.metrics import f1_score
>>> y_true = [0, 1, 2, 0, 1, 2]
>>> y_pred = [0, 2, 1, 0, 0, 1]
>>> f1_score(y_true, y_pred, average='macro')  
0.26...
>>> f1_score(y_true, y_pred, average='micro')  
0.33...
>>> f1_score(y_true, y_pred, average='weighted')  
0.26...
>>> f1_score(y_true, y_pred, average=None)
array([ 0.8,  0. ,  0. ])

回歸問題

平均絕對誤差

將各個(gè)樣本的絕對誤差匯總履澳,然后根據(jù)數(shù)據(jù)點(diǎn)數(shù)量求出平均誤差嘶窄。通過將模型的所有絕對值加起來,可以避免因預(yù)測值比真實(shí)值過高或或低抵消誤差奇昙,并能獲得用戶評估模型的整體誤差指標(biāo)护侮。

>>> from sklearn.metrics import mean_absolute_error
>>> y_true = [3, -0.5, 2, 7]
>>> y_pred = [2.5, 0.0, 2, 8]
>>> mean_absolute_error(y_true, y_pred)
0.5
>>> y_true = [[0.5, 1], [-1, 1], [7, -6]]
>>> y_pred = [[0, 2], [-1, 2], [8, -5]]
>>> mean_absolute_error(y_true, y_pred)
0.75
>>> mean_absolute_error(y_true, y_pred, multioutput='raw_values')
array([ 0.5,  1. ])
>>> mean_absolute_error(y_true, y_pred, multioutput=[0.3, 0.7])
... 
0.849...
均方誤差

與絕對誤差相比敌完,殘差(預(yù)測值與真實(shí)值的差值)被求平方储耐。對殘差求平方的一些好處是,自動(dòng)將所有的誤差轉(zhuǎn)為正數(shù)滨溉、注重較大的誤差而不是較小的誤差以及在微積分中是可微單(可讓我們找到最大值和最小值)什湘。

>>> from sklearn.metrics import mean_squared_error
>>> y_true = [3, -0.5, 2, 7]
>>> y_pred = [2.5, 0.0, 2, 8]
>>> mean_squared_error(y_true, y_pred)
0.375
>>> y_true = [[0.5, 1],[-1, 1],[7, -6]]
>>> y_pred = [[0, 2],[-1, 2],[8, -5]]
>>> mean_squared_error(y_true, y_pred)  
0.708...
>>> mean_squared_error(y_true, y_pred, multioutput='raw_values')
... 
array([ 0.416...,  1.        ])
>>> mean_squared_error(y_true, y_pred, multioutput=[0.3, 0.7])
... 
0.824...
R2分?jǐn)?shù)
>>> from sklearn.metrics import r2_score
>>> y_true = [3, -0.5, 2, 7]
>>> y_pred = [2.5, 0.0, 2, 8]
>>> r2_score(y_true, y_pred)  
0.948...
>>> y_true = [[0.5, 1], [-1, 1], [7, -6]]
>>> y_pred = [[0, 2], [-1, 2], [8, -5]]
>>> r2_score(y_true, y_pred, multioutput='variance_weighted')  
0.938...
>>> y_true = [1,2,3]
>>> y_pred = [1,2,3]
>>> r2_score(y_true, y_pred)
1.0
>>> y_true = [1,2,3]
>>> y_pred = [2,2,2]
>>> r2_score(y_true, y_pred)
0.0
>>> y_true = [1,2,3]
>>> y_pred = [3,2,1]
>>> r2_score(y_true, y_pred)
-3.0
可釋方差分?jǐn)?shù)
>>> from sklearn.metrics import explained_variance_score
>>> y_true = [3, -0.5, 2, 7]
>>> y_pred = [2.5, 0.0, 2, 8]
>>> explained_variance_score(y_true, y_pred)  
0.957...
>>> y_true = [[0.5, 1], [-1, 1], [7, -6]]
>>> y_pred = [[0, 2], [-1, 2], [8, -5]]
>>> explained_variance_score(y_true, y_pred, multioutput='uniform_average')
... 
0.983...

網(wǎng)格搜索和交叉驗(yàn)證

在Udacity的Reviewer督促下,終于搞懂了網(wǎng)格搜索和交叉驗(yàn)證以及它們是如何工作的晦攒。

機(jī)器學(xué)習(xí)的很多算法需要尋找最優(yōu)參數(shù)闽撤,進(jìn)行模型改進(jìn),網(wǎng)格搜索可以找到算法的最有參數(shù)脯颜。
網(wǎng)格搜索會遍歷傳入的參數(shù)字典中參數(shù)的所有可能情況哟旗,根據(jù)傳入的scoring對參數(shù)進(jìn)行打分,返回一個(gè)網(wǎng)格搜索類的對象栋操,至于要用該對象的哪個(gè)值就視需要而定了闸餐。

交叉驗(yàn)證可以讓網(wǎng)格搜索在不碰測試集的前提下進(jìn)行模型驗(yàn)證。交叉驗(yàn)證有很多種矾芙,比如k折交叉驗(yàn)證舍沙,它將訓(xùn)練集平均分成k份,其中1份做測試集剔宪,其余k-1份做訓(xùn)練集拂铡,運(yùn)行k次壹无,得出一個(gè)平均分作為打分。網(wǎng)格搜索結(jié)合交叉驗(yàn)證的思路就是:把網(wǎng)格搜索找到的所有參數(shù)在k份驗(yàn)證集上跑一遍感帅,將分?jǐn)?shù)最好的作為最優(yōu)參數(shù)斗锭。用交叉驗(yàn)證最大的好處就是不碰測試集。

下面代碼是我在做Udacity的波士頓房價(jià)預(yù)測后面的可選問題——北京房價(jià)預(yù)測的代碼失球。用的是k折交叉驗(yàn)證和網(wǎng)格搜索拒迅。

def fit_model_k_fold(X, y):
    """ Performs grid search over the 'max_depth' parameter for a 
        decision tree regressor trained on the input data [X, y]. """
    
    # Create cross-validation sets from the training data
    # cv_sets = ShuffleSplit(n_splits = 10, test_size = 0.20, random_state = 0)
    k_fold = KFold(n_splits=10)
    
    # TODO: Create a decision tree regressor object
    regressor = DecisionTreeRegressor(random_state=80)

    # TODO: Create a dictionary for the parameter 'max_depth' with a range from 1 to 10
    params = {'max_depth':range(1,11)}

    # TODO: Transform 'performance_metric' into a scoring function using 'make_scorer' 
    scoring_fnc = make_scorer(performance_metric)

    # TODO: Create the grid search object
    grid = GridSearchCV(regressor, param_grid=params,scoring=scoring_fnc,cv=k_fold)

    # Fit the grid search object to the data to compute the optimal model
    grid = grid.fit(X, y)

    # Return the optimal model after fitting the data
    return grid.best_estimator_


reg_k_fold = fit_model_k_fold(X_train, y_train)
print "k_fold Parameter 'max_depth' is {} for the optimal model.".format(reg_k_fold.get_params()    ['max_depth'])
# Show predictions
for i, price in enumerate(reg_k_fold.predict(client_data)):
     print "k_fold Predicted selling price for Client {}'s home: ¥{:,.2f}萬".format(i+1, price)
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市她倘,隨后出現(xiàn)的幾起案子璧微,更是在濱河造成了極大的恐慌,老刑警劉巖硬梁,帶你破解...
    沈念sama閱讀 206,378評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件前硫,死亡現(xiàn)場離奇詭異,居然都是意外死亡荧止,警方通過查閱死者的電腦和手機(jī)屹电,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,356評論 2 382
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來跃巡,“玉大人危号,你說我怎么就攤上這事∷匦埃” “怎么了外莲?”我有些...
    開封第一講書人閱讀 152,702評論 0 342
  • 文/不壞的土叔 我叫張陵,是天一觀的道長兔朦。 經(jīng)常有香客問我偷线,道長,這世上最難降的妖魔是什么沽甥? 我笑而不...
    開封第一講書人閱讀 55,259評論 1 279
  • 正文 為了忘掉前任声邦,我火速辦了婚禮,結(jié)果婚禮上摆舟,老公的妹妹穿的比我還像新娘亥曹。我一直安慰自己,他們只是感情好恨诱,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,263評論 5 371
  • 文/花漫 我一把揭開白布媳瞪。 她就那樣靜靜地躺著,像睡著了一般胡野。 火紅的嫁衣襯著肌膚如雪材失。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,036評論 1 285
  • 那天硫豆,我揣著相機(jī)與錄音龙巨,去河邊找鬼笼呆。 笑死,一個(gè)胖子當(dāng)著我的面吹牛旨别,可吹牛的內(nèi)容都是我干的诗赌。 我是一名探鬼主播,決...
    沈念sama閱讀 38,349評論 3 400
  • 文/蒼蘭香墨 我猛地睜開眼秸弛,長吁一口氣:“原來是場噩夢啊……” “哼铭若!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起递览,我...
    開封第一講書人閱讀 36,979評論 0 259
  • 序言:老撾萬榮一對情侶失蹤叼屠,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后绞铃,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體镜雨,經(jīng)...
    沈念sama閱讀 43,469評論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 35,938評論 2 323
  • 正文 我和宋清朗相戀三年儿捧,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了荚坞。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 38,059評論 1 333
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡菲盾,死狀恐怖颓影,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情懒鉴,我是刑警寧澤诡挂,帶...
    沈念sama閱讀 33,703評論 4 323
  • 正文 年R本政府宣布,位于F島的核電站疗我,受9級特大地震影響咆畏,放射性物質(zhì)發(fā)生泄漏南捂。R本人自食惡果不足惜吴裤,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,257評論 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望溺健。 院中可真熱鬧麦牺,春花似錦、人聲如沸鞭缭。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,262評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽岭辣。三九已至吱晒,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間沦童,已是汗流浹背仑濒。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評論 1 262
  • 我被黑心中介騙來泰國打工叹话, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人墩瞳。 一個(gè)月前我還...
    沈念sama閱讀 45,501評論 2 354
  • 正文 我出身青樓驼壶,卻偏偏與公主長得像,于是被迫代替她去往敵國和親喉酌。 傳聞我的和親對象是個(gè)殘疾皇子热凹,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,792評論 2 345

推薦閱讀更多精彩內(nèi)容