【轉】機器學習模型評價1(Evaluating Machine Learning Models)

博客上看到一篇優秀的翻譯文章。文章地址:http://blog.csdn.net/heyongluoyao8/article/details/49408319#
機器學習模型評價(Evaluating Machine Learning Models)-主要概念與陷阱
前言
??本文主要解釋一些關于機器學習模型評價的主要概念,與評價中可能會遇到的一些陷阱。如訓練集-驗證集二劃分校驗(Hold-out validation)、交叉校驗(Cross-validation)、超參數調優(hyperparameter tuning)等。這三個術語都是從不同的層次對機器學習模型進行校驗。Hold-out validation與Cross-validation是將模型能夠更好得對將來的數據(unseen data)進行擬合而采用的方法。Hyperparameter tuning是一種模型選擇方法。 ??機器學習是一門跨學科領域,涉及到統計學、計算機科學、最優化理論、信息理論、神經科學、理論物理以及其他領域。同時,機器學習也是一門非常年輕的學科。機器學習的大規模應用僅僅開始于過去二十年。當今,數據科學應用已成為一種職業。就像西部開發一樣,擁有則無盡的機會,同時也有伴隨著很多迷惑與問題。 ??本文將從以下部分對機器學習模型的評價進行介紹: * 介紹模型離線與在線評價體系與知識; * 介紹一些不同類別下得機器學習模型評價指標,如分類回歸、排序等。 * 介紹訓練目標、模型驗證指標的區別 * 介紹解決數據傾斜的一些方法以及模型參數調優的方法 * 最后介紹一些工具,如GraphLab與Dato等。
機器學習Workflow
??一般的,機器學習過程包括兩個階段,分別為:原型設計階段(Prototyping)與應用階段(Deployed),與軟件開發類似的Debug與Release階段。如下圖所示: ![](./屏幕快照 2015-09-26 下午4.30.10.png) Prototyping階段是使用歷史數據訓練一個適合解決目標任務的一個或多個機器學習模型,并對模型進行驗證(Validation)與離線評估(Offline evalutation),然后通過評估指標選擇一個較好的模型。如在分類任務中,選擇一個適合自己問題的最好的分類算法。Deployed階段是當模型達到設定的指標值時便將模型上線,投入生產,使用新生成的數據來對該模型進行在線評估(Online evalution),以及使用新數據更新模型。在對模型進行離線評估或者在線評估時,它們所用的評價指標往往不同。如在離線評估中,我們精彩使用的有準確率(accuracy)、精確率-召回率(precision-recall),而在在線評估中,一般使用一些商業評價指標,如用戶生命周期值(customer lifetime value)、廣告點擊率(click through rate)、用戶流失率(customer churn rate)等,這些指標才是模型使用者最終關心的一些指標。甚至在對模型進行訓練和驗證過程中使用的評價指標都不一樣。 ??同時我們注意到,在這兩個階段使用的數據集也不一樣,分別是歷史數據(historical data)與新數據(live data)。在機器學習中,很多模型都是假設數據的分布是一定的,不變的,即歷史數據與將來的數據都服從相同的分布。但是,在現實生活中,這種假設往往是不成立的,即數據的分布會隨著時間的移動而改變,有時甚至變化得很急劇,這種現象稱為分布漂移(Distribution Drift)。例如,在文章推薦系統中,文章的主題集數目和主題的發生頻率可能是每天改變的,甚至每個小時都在改變,昨天流行的主題在今天可能就不再流行了。如在新聞推薦中,新聞主題就變更得非常快。因此在進行模型構建之時,我們需要去撲捉分布漂移信息并使自己的模型能夠應對這種情況。一個常用的方法便是使用一些驗證指標對模型在不斷新生的數據集上進行性能跟蹤。如果指標值能夠達到模型構建時的指標值,那么表示模型能夠繼續對當前數據進行擬合。當性能開始下降時,說明該模型已經無法擬合當前的數據了,因此需要對模型進行重新訓練了。 ??不同的機器學習任務有著不同的性能評價指標。例如,在垃圾郵件檢測系統中,它本身是一個二分類問題(垃圾郵件vs正常郵件),可以使用準確率(Accuracy)、對數損失函數(log-loss)、AUC等評價方法。又如在股票預測中,它本身是一個實數序列數據預測問題,可以使用平方根誤差(root mean square error, RMSE)等指標;又如在搜索引擎中進行與查詢相關的項目排序中,可以使用精確率-召回率(precision-recall)、NDCG(normalized discounted cumulative gain)。 ??正如前面所提到的那樣,在原型階段中最重要的任務便是選擇一個正確的適合的模型對數據進行擬合。而當模型訓練完畢后,我們需要使用一個與訓練數據集獨立的新的數據集去對模型進行驗證。因為模型本身就是使用訓練數據集訓練出來的,因此它已經對訓練集進行了很好的擬合,但是它在新的數據集上的效果則有待驗證,因此需要使用新的與訓練集獨立的數據集對模型進行訓練,確保該模型在新的數據集上也能夠滿足要求。模型能夠對新的數據也能work稱為模型的泛化能力。 ??那么新的數據集如何得來呢?一般的解決方法是將已有的數據集隨機劃分成兩個個部分,一個用來訓練模型,另一個用來驗證與評估模型。另一種方法是重采樣,即對已有的數據集進行有放回的采樣,然后將數據集隨機劃分成兩個部分,一個用來訓練,一個用來驗證。至于具體的做法有hold-out validation、k-fold cross-validation、bootstrapping與jackknife resampling,后面會進行詳細介紹。 ??機器學習模型建立過程其實是一個參數學習與調優的過程。對模型進行訓練,便是模型參數的學習更新過程。模型出了這些常規參數之外,還存在超參數(hyperparameters)。它們之間有何區別呢?簡而言之,模型參數使指通過模型訓練中的學習算法而進行調整的,而模型超參數不是通過學習算法而來的,但是同樣也需要進行調優。舉例,我們在對垃圾郵件檢測進行建模時,假設使用logistic回歸。那么該任務就是在特征空間中尋找能夠將垃圾郵件與正常郵件分開的logistic函數位置,于是模型訓練的學習算法便是得到各個特征的權值,從而決定函數的位置。但是該學習算法不會告訴我們對于該任務需要使用多少個特征來對一封郵件進行表征,特征的數目這個參數便是該模型的超參數。 ??超參數的調優是一個相當復雜與繁瑣的任務。在模型原型設計階段,需要嘗試不同的模型、不同的超參數意見不同的特征集,我們需要尋找一個最優的超參數,因此需要使用相關的搜索算法去尋找,如格搜索(grid search)、隨機搜索(random search)以及啟發式搜索(smart search)等。這些搜索算法是從超參數空間中尋找一個最優的值。本文后面會進行詳細介紹。 ??當模型使用離線數據訓練好并滿足要求后,就需要將模型使用新的在線數據進行上線測試,這就是所謂的在線測試。在線測試不同于離線測試,有著不同的測試方法以及評價指標。最常見的便是A/B testing,它是一種統計假設檢驗方法。不過,在進行A/B testing的時候,會遇到很多陷阱與挑戰,具體會在本文后面進行詳細介紹。另一個相對使用較小的在線測試方法是multiarmed bandits。在某些情況下,它比A/B testing的效果要好。后面會進行具體講解。
評價指標(Evaluation metrics)
??評價指標是機器學習任務中非常重要的一環。不同的機器學習任務有著不同的評價指標,同時同一種機器學習任務也有著不同的評價指標,每個指標的著重點不一樣。如分類(classification)、回歸(regression)、排序(ranking)、聚類(clustering)、熱門主題模型(topic modeling)、推薦(recommendation)等。并且很多指標可以對多種不同的機器學習模型進行評價,如精確率-召回率(precision-recall),可以用在分類、推薦、排序等中。像分類、回歸、排序都是監督式機器學習,本文的重點便是監督式機器學習的一些評價指標。
分類評價指標
??分類是指對給定的數據記錄預測該記錄所屬的類別。并且類別空間已知。它包括二分類與多分類,二分類便是指只有兩種類別,如垃圾郵件分類中便是二分類問題,因為類別空間只有垃圾郵件和非垃圾郵件這兩種,可以稱為“負”(negative)與正(positive)兩種類別,一般在實際計算中,將其映射到“0”-“1” class中;而多分類則指類別數超過兩種。下面主要根據二分類的評價指標進行講解,不過同時它們也可擴展到多分類任務中。下面對分類中一些常用的評價指標進行介紹。
準確率(Accuracy)
??準確率是指在分類中,使用測試集對模型進行分類,分類正確的記錄個數占總記錄個數的比例:
accuracy=ncorrectntotal

準確率看起來非常簡單。然而,準確率評價指標沒有對不同類別進行區分,即其平等對待每個類別。但是這種評價有時是不夠的,比如有時要看類別0與類別1下分類錯誤的各自個數,因為不同類別下分類錯誤的代價不同,即對不同類別的偏向不同,比如有句話為“寧可錯殺一萬,不可放過一千“就是這個道理,例如在病患診斷中,診斷患有癌癥實際上卻未患癌癥(False Positive)與診斷未患有癌癥的實際上卻患有癌癥(False Negative)的這兩種情況的重要性不一樣。。另一個原因是,可能數據分布不平衡,即有的類別下的樣本過多,有的類別下的樣本個數過少,兩類個數相差較大。這樣,樣本占大部分的類別主導了準確率的計算,為了解決這個問題,對準確率進行改進,得到平均準確率。
平均準確率(Average Per-class Accuracy)
??為了應對每個類別下樣本的個數不一樣的情況,對準確率進行變種,計算每個類別下的準確率,然后再計算它們的平均值。舉例,類別0的準確率為80%,類別1下的準確率為97.5%,那么平均準確率為(80%+97.5%)/2=88.75%。因為每個類別下類別的樣本個數不一樣,即計算每個類別的準確率時,分母不一樣,則平均準確率不等于準確率,如果每個類別下的樣本個數一樣,則平均準確率與準確率相等。 ??平均準確率也有自己的缺點,比如,如果存在某個類別,類別的樣本個數很少,那么使用測試集進行測試時(如k-fold cross validation),可能造成該類別準確率的方差過大,意味著該類別的準確率可靠性不強。
對數損失函數(Log-loss)
??在分類輸出中,若輸出不再是0-1,而是實數值,即屬于每個類別的概率,那么可以使用Log-loss對分類結果進行評價。這個輸出概率表示該記錄所屬的其對應的類別的置信度。比如如果樣本本屬于類別0,但是分類器則輸出其屬于類別1的概率為0.51,那么這種情況認為分類器出錯了。該概率接近了分類器的分類的邊界概率0.5。Log-loss是一個軟的分類準確率度量方法,使用概率來表示其所屬的類別的置信度。Log-loss具體的數學表達式為:
log_loss=?1N∑i=1Nyilogpi+(1?yi)log(1?pi)

其中,yi
是指第i
個樣本所屬的真實類別0或者1,pi
表示第i
個樣本屬于類別1的概率,這樣上式中的兩個部分對于每個樣本只會選擇其一,因為有一個一定為0,當預測與實際類別完全匹配時,則兩個部分都是0,其中假定0log0=0。 ??其實,從數學上來看,Log-loss的表達式是非常漂亮的。我們仔細觀察可以發現,其信息論中的交叉熵(Cross Entropy,即真實值與預測值的交叉熵),它與相對熵(Relative Entropy,也稱為KL距離或KL散度, Kullback–Leibler divergence.)也非常像。信息熵是對事情的不確定性進行度量,不確定越大,熵越大。交叉熵包含了真實分布的熵加上假設與真實分布不同的分布的不確定性。因此,log-loss是對額外噪聲(extra noise)的度量,這個噪聲是由于預測值域實際值不同而產生的。因此最小化交叉熵,便是最大化分類器的準確率。
精確率-召回率(Precision-Recall)
??精確率-召回率其實是兩個評價指標。但是它們一般都是同時使用。精確率是指分類器分類正確的正樣本的個數占該分類器所有分類為正樣本個數的比例。召回率是指分類器分類正確的正樣本個數占所有的正樣本個數的比例。
F1-score:
??F1-score為精確率與召回率的調和平均值,它的值更接近于Precision與Recall中較小的值。即:
F1=2?precision?recallprecision+recall

AUC(Area under the Curve(Receiver Operating Characteristic, ROC))
??AUC的全稱是Area under the Curve,即曲線下的面積,這條曲線便是ROC曲線,全稱為the Receiver Operating Characteristic曲線,它最開始使用是上世紀50年代的電信號分析中,在1978年的“Basic Principles of ROC Analysis ”開始流行起來。ROC曲線描述分類器的True Positive Rate(TPR,分類器分類正確的正樣本個數占總正樣本個數的比例)與False Positive Rate(FPR,分類器分類錯誤的負樣本個數占總負樣本個數的比例)之間的變化關系。如下圖所示: ![](./屏幕快照 2015-09-27 下午12.42.54.png) 如上圖,ROC曲線描述FPR不斷變化時,TPR的值,即FPR與TPR之間的關系曲線。顯而易見,最好的分類器便是FPR=0%,TPR=100%,但是一般在實踐中一個分類器很難會有這么好的效果,即一般TPR不等于1,FPR不等于0的。當使用ROC曲線對分類器進行評價時,如果對多個分類器進行比較時,如果直接使用ROC曲線很難去比較,只能通過將ROC分別畫出來,然后進行肉眼比較,那么這種方法是非常不便的,因此我們需要一種定量的指標去比較,這個指標便是AUC了,即ROC曲線下的面積,面積越大,分類器的效果越好,AUC的值介于0.5到1.0之間。 ??具體如何描繪ROC曲線,如在二分類中,我們需要設定一個閾值,大于閾值分類正類,否則分為負類。因此,我們可以變化閾值,根據不同的閾值進行分類,根據分類結果計算得到ROC空間中的一些點,連接這些點就形成ROC曲線。ROC曲線會經過(0,0)與(1,1)這兩點,實際上這兩點的連線形成的ROC代表一個隨機分類器,一般情況下分類器的ROC曲線會在這條對角連線上方。 ??在ROC曲線中,點(0,0)表示TPR=0,FPR=0,即分類器將每個實例都預測為負類;點(1,1)表示TPR=1,FPR=1,即分類器將每個實例都預測為正類;點(0,0)表示TPR=1,FPR=0,即分類器將每個正類實例都預測為正類,將每個負類實例都預測為負類,這是一個理想模型。 ??ROC曲線有個很好的特性:當測試集中的正負樣本的分布變化的時候,ROC曲線能夠保持不變。在實際的數據集中,經常會出現類別不平衡(class imbalance)現象,即負樣本比正樣本少很多(或者相反),而且測試數據集中的正負樣本的分布也可能隨時間發生變化。關于ROC與AUC更多的講解,參見這里
混淆矩陣(Confusion Matrix)
??混淆矩陣是對分類的結果進行詳細描述的一個表,無論是分類正確還是錯誤,并且對不同的類別進行了區分,對于二分類則是一個22的矩陣,對于n分類則是nn的矩陣。對于二分類,第一行是真實類別為“Positive”的記錄個數(樣本個數),第二行則是真實類別為“Negative”的記錄個數,第一列是預測值為“Positive”的記錄個數,第二列則是預測值為“Negative”的記錄個數。如下表所示:
?
Predicted as Positive
Predicted as Negative

Labeled as Positive
True Positive(TP)
False Negative(FN)

Labeled as Negative
False Positive(FP)
True Negative(TN)

如上表,可以將結果分為四類: * 真正(True Positive, TP):被模型分類正確的正樣本; * 假負(False Negative, FN):被模型分類錯誤的正樣本; * 假正(False Positive, FP):被模型分類的負樣本; * 真負(True Negative, TN):被模型分類正確的負樣本;
進一步可以推出這些指標: * 真正率(True Positive Rate, TPR),又名靈敏度(Sensitivity):分類正確的正樣本個數占整個正樣本個數的比例,即:TPR=TPTP+FN

  • 假負率(False Negative Rate, FNR):分類錯誤的正樣本的個數占正樣本的個數的比例,即:FNR=FNTP+FN
  • 假正率(False Positive Rate, FPR):分類錯誤的負樣本個數占整個負樣本個數的比例,即:FPR=FPFP+TN
  • 真負率(True Negative Rate, TNR):分類正確的負樣本的個數占負樣本的個數的比例,即:TNR=TNFP+TN

進一步,由混淆矩陣可以計算以下評價指標: * 準確率(Accuracy):分類正確的樣本個數占所有樣本個數的比例,即:
accuracy=TP+TNTP+FN+FP+TN

  • 平均準確率(Average per-class accuracy):每個類別下的準確率的算術平均,即: average_accuracy=TPTP+FN+TNTN+FP2

  • 精確率(Precision):分類正確的正樣本個數占分類器所有的正樣本個數的比例,即: Precision=TPTP+FP

  • 召回率(Recall):分類正確的正樣本個數占正樣本個數的比例,即: Recall=TPTP+FN

  • F1-Score:精確率與召回率的調和平均值,它的值更接近于Precision與Recall中較小的值,即: F1=2?precision?recallprecision+recall

  • ROC曲線 ROC曲線的x軸便是FPR,y軸便是TPR。
    回歸評價指標
    ??與分類不同的是,回歸是對連續的實數值進行預測,即輸出值是連續的實數值,而分類中是離散值。例如,給你歷史股票價格,公司與市場的一些信息,需要你去預測將來一段時間內股票的價格走勢。那么這個任務便是回歸任務。對于回歸模型的評價指標主要有以下幾種: * RMSE ??回歸模型中最常用的評價模型便是RMSE(root mean square error,平方根誤差),其又被稱為RMSD(root mean square deviation),其定義如下:
    RMSE=∑ni=0(yi?yi^)2n ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄√

其中,yi
是第i
個樣本的真實值,yi^
是第i
個樣本的預測值,n
是樣本的個數。該評價指標使用的便是歐式距離。 ??RMSE雖然廣為使用,但是其存在一些缺點,因為它是使用平均誤差,而平均值對異常點(outliers)較敏感,如果回歸器對某個點的回歸值很不理性,那么它的誤差則較大,從而會對RMSE的值有較大影響,即平均值是非魯棒的。 * Quantiles of Errors ??為了改進RMSE的缺點,提高評價指標的魯棒性,使用誤差的分位數來代替,如中位數來代替平均數。假設100個數,最大的數再怎么改變,中位數也不會變,因此其對異常點具有魯棒性。 ??在現實數據中,往往會存在異常點,并且模型可能對異常點擬合得并不好,因此提高評價指標的魯棒性至關重要,于是可以使用中位數來替代平均數,如MAPE: MAPE=median(|yi?yi^|/yi)

MAPE是一個相對誤差的中位數,當然也可以使用別的分位數。 * “Almost Crrect” Predictions ??有時我們可以使用相對誤差不超過設定的值來計算平均誤差,如當|yi?yi^|/yi
超過100%(具體的值要根據問題的實際情況)則認為其是一個異常點,,從而剔除這個異常點,將異常點剔除之后,再計算平均誤差或者中位數誤差來對模型進行評價。
排序評價指標
??排序任務指對對象集按照與輸入的相關性進行排序并返回排序結果的過程。舉例,我們在使用搜索引擎(如google,baidu)的時候,我們輸入一個關鍵詞或多個關鍵詞,那么系統將按照相關性得分返回檢索結果的頁面。此時搜索引擎便是一個排序器。其實,排序也可以說是一個二分類問題。即將對象池中的對象分為與查詢詞相關的正類與不相關的負類。并且每一個對象都有一個得分,即其屬于正類的置信度,然后按照這個置信度將正類進行排序并返回。 ??另一個與排序相關的例子便是個性化推薦引擎。個性化推薦引擎便是根據用戶的歷史行為信息或者元信息計算出每個用戶當前有興趣的項目,并為每個項目賦一個興趣值,最好按照這個興趣值進行排序,返回top n興趣項目。 ??對排序器進行評價的一下指標如下: * Precision-Recall精確率-召回率 ??精確率-召回率已經在分類器的評價指標中介紹過。它們同樣也可以用于對排序器進行評價。如下圖所示: ![](./屏幕快照 2015-09-27 下午7.01.28.png)
precision=happy correct answerstotal items returned by ranker

recall=happy correct answerstotal relevant items

一般的,排序器返回top k的items,如k=5, 10, 20, 100等。那么該評價指標改為“precision@k”和“recall@k”。 ??在推薦系統中,它相當于一個多興趣查詢,即每個用戶是一個查詢詞,然后返回每個查詢詞相關的top k項目,即返回每個用戶感興趣的top k項目,那么在計算評價指標值時,則需要對每個用戶的精確率與召回率進行平均(average precision@k” and “average recall@k”),將平均值作為模型的精確率與召回率。 * Precision-Recall Curve和F1 Score ??當我們改變top k中的k值時,便可以得到不同的精確率與召回率,那么我們可以通過改變k值而得到精確率曲線和召回率曲線。與ROC曲線一樣,我們也需要一個定量的指標對其ROC曲線進行描述而來評價其對應的模型進行評價。可取多個k值,然后計算其評價的精確率與召回率。 ??除了Precision-Recall曲線外,另一個便是F1 Score,在分類器評價指標中也有提及到,它將精確度與召回率兩個指標結合起來,如下: F1=2?precision?recallprecision+recall

F1-score是精確率與召回率的調和平均值,它的值更接近于Precision與Recall中較小的值。 * NDCG ??在精確率與召回率中,返回集中每個項目的地位(權值)是一樣,即位置k處的項目與位置1處的項目地位一樣,但是實際情況應該是越排在前面的項目越相關,得分越高。NDCG(normalized discounted cumulative gain)指標便考慮了這種情況,在介紹NDCG之前,首先介紹一下CG(cumulative gain與DCG(discounted cumulative gain)。CG是對排序返回的top k個項目的相關性(即得分)求和,而DCG在每個項目的得分乘上一個權值,該權值與位置成反方向(如成反比),即位置越近,權值越大。而NDCG則對每項的帶權值得分先進行歸一化,然后再求和。 ??在信息檢索中或者那些對項目的返回位置關心的模型中經常使用DCG或NDCG。
注意事項
數據傾斜
??在對模型進行評價的時候,數據的好壞往往對評價指標有著很大的影響。其中數據傾斜便是一個常見的數據特征,具體指分類中每個類別的數據量不均衡,相差較大,存在一些異常點,這些異常點會對評價指標的計算產生較大的影響等。
類別不均衡(Imbalanced Classes)
??在前面我們提到使用average per-class accuracy(平均類別準確率)來解決類別不均衡所帶來的評價指標問題。舉例:假設數據集中正類的數據記錄數占總記錄數的1%(現實世界中如廣告系統中的點擊率CTR、推薦系統中的發生行為的用戶-項目對、惡意軟件檢測中的惡意軟件),那么這種情況下,如果將所有對象都預測為負類,那么準確率則為99%,然而一個好的分類器準確率應該超過99%。在ROC曲線中,只有左上角的那個部分菜重要,如下圖所示: ![](./屏幕快照 2015-09-27 下午10.10.00.png) ??如果評價指標對待每一個類別下的每一個實例都采用相等的權值,那么就很難處理類別不平衡問題。因為此時評價指標會被數據量大的類別占主導,起決定性作用。并且不止是影響模型評價階段,而且會影響模型的訓練階段。如果數據的類別不平衡不做處理,那么就會影響到對小類別的數據記錄的分類。 ??例如在推薦系統中,真實的數據中,有行為的用戶-項目對很少,即大部分用戶有發生行為的項目量很少,以及大部分項目只有少量的用戶在上面有行為。這兩個問題會對推薦系統模型的訓練與評價都會產生影響,但訓練數據很少時,模型很難學習都用戶的偏好,或者項目的興趣相似項目量很少,導致在對模型進行評價時會得到一個很低的評價指標值,即會得到一個性能較差的推薦模型。
異常點(Outliers)
??異常點是另一種數據傾斜問題。值大的異常點會對回歸造成很大的影響與問題。例如,Million Song Dataset中,一個用戶對一首歌曲的評分為該用戶聽這首歌曲的次數,回歸模型的預測得分中最高得分竟然超過了16000分,這說明回歸模型出現了一些問題,并且導致其它的誤差相對于該誤差都是極小的。我們可以使用誤差的中位數來減少這個異常點所所帶來的影響。從而增加魯棒性。但是該方法不能解決在模型訓練階段的該問題。有效的解決方法是在數據預處理階段對數據進行數據清洗從而剔除異常點,以及對人物進行重新定義與建模,使得其對異常低能不敏感。
離線評價機制
??在模型的原型設計階段包:特征選擇、模型類型的選擇、模型訓練等。該部分內容仍然放在模型的原型設計階段。
模型訓練(Training)、驗證(Validation)與模型選擇(Model Selection)
??我們在解決機器學習任務之時,需要選擇一個合適正確的模型去擬合數據,模型的選擇發生在模型的驗證階段而不是模型的訓練階段。即當我們訓練出多個模型之時,需要選擇一個較好的模型,具體而言,便是使用一個新的數據集(稱為驗證數據集)去對每個模型進行評價,選擇一個最優的模型,最優不止是指效果,還有模型復雜度,模型可實踐性等方面。如下圖所示: ![](./屏幕快照 2015-09-27 下午10.56.23.png) 在上圖中,超參數調優(hyperparameter tuning )作為控制模型訓練的一個元過程(“meta” process),即前奏過程,將會在后面詳細介紹。圖中將歷史數據集劃分成兩個部分(一般是隨機劃分),一個作為模型的訓練集,一個作為模型的驗證數據集。模型訓練階段使用訓練集來訓練模型并輸出之,然后使用驗證集對該模型進行評價。并將驗證結果反饋到超參數調優器中,對超參數進行調優后繼續訓練模型。 ?? 為何要將歷史數據劃分為兩個數據集呢?在統計模型世界中,任何事物的發生都假設是隨機的,它們服從一個隨機分布。模型便是從隨機數據中學習而來的,因此模型也是隨機的。并且這個學習的模型需要被一個隨機的已觀察到的數據集進行測試評估,因此測試結果也是隨機的。為了確保準確性與公平性,需要使用一個與訓練集獨立的數據集對模型進行驗證。必須使用與訓練樣本集不同的數據樣本集進行測試,從而可以得到模型的泛化誤差。那么如何產生一個新的數據集呢? ??在離線階段,我們只有一個歷史數據集合。那么如何去獲得另一個獨立的數據集呢?因此我們需要一種機制去產生另一個數據集。一種方式是留下一部分數據來作為驗證集,如hold-out validation與cross-validation, 另一種方式是重采樣技術,如bootstrapping與Jackknife。如下圖所示: ![](./屏幕快照 2015-09-27 下午11.26.11.png) ??從上圖可以看出,cross-validation與bootstrapping都是將數據集劃分為多個較小的數據集,而hold-out validation只是將數據集劃分為一大一小的兩個部分,大的部分作為訓練集,較小的部分作為驗證集。
Hold-out Validation
??Hold-out Validation較簡單,它假設數據集中的每個數據點都是獨立同分布的(i.i.d,independently and identically distributed)。因此我們只需要簡單得將原數據集隨機劃分成兩個部分,較大的部分作為訓練集,用來訓練數據,較小的部分作為驗證集,用來對模型進行驗證。 ??從計算的角度來說,Hold-out Validation是簡單的并運行時間快的。缺點便是它是強假設的,缺乏有效的統計特征,并且驗證數據集較小,那么其驗證的結果則可靠性較低,同時也很難在單個數據集上計算方差信息與置信區間。因此如果需要使用 hold-out validation方法,則需要足夠的數據以確保驗證集數據足夠而確保可靠的統計估計。
Cross-Validation
??Cross-Validation是另一種模型訓練集與驗證集的產生方法,即將數據集劃分成多個小部分集合,如劃分成k個部分,那么就變為了k-fold cross validation。依次使用其中的k-1個數據集對模型進行訓練(每次使用k-1個不同的數據集),然后使用剩下的一個數據集對模型進行評價,計算評價指標值。接著重復前面的步驟,重復k次,得到k個評價指標值。最后計算這k個評價指標的平均值。其中k是一個超參數,我們可以嘗試多個k,選擇最好的平均評價指標值所對應的k為最終的k值。 ??另一個Cross-Validation的變種便是leave-one-out。該方法與k-fold cross validation方法類似,只是k等于數據集中樣本的總數目,即每次使用n-1個數據點對模型進行訓練,使用最好一個數據點對模型進行訓練。重復n次,計算每次的評價指標值,最后得到平均評價指標值。該方法又稱為n-fold cross validation。 ??當數據集較小時以致hold-out validation效果較差的時候,cross validation是一種非常有效的訓練集-驗證集產生方法。
Bootstrapping和Jackknife
??Bootstrapping是一種重采樣技術,翻譯成自助法。它通過采樣技術從原始的單個數據集上產生多個新的數據集,每個新的數據集稱為一個bootstrapped dataset,并且每個新的數據集大小與原始數據集大小相等。這樣,每個新的數據集都可以用來對模型進行評價,從而可以得到多個評價值,進一步可以得到評價方差與置信區間。 ??Bootstrapping與Cross Validation交叉校驗相關。Bootstrapping對原數據集進行采樣生成一個新的數據集( bootstrapped dataset)。不同的是,Bootstrapping假設每個數據點都服從均勻分布。它采用的是一種有放回的采樣,即將原始數據集通過采樣生成一個新的數據集時,每次采樣都是有放回得采樣,那么這樣在新生成的數據集中,可能存在重復的數據點,并且可能會重復多次。 ??為什么使用有放回的采樣?每一個樣本都可以用一個真實的分布進行描述,但是該分布我們并不知道,我們只有一個數據集去推導該分布,因此我們只能用該數據集去估計得到一個經驗分布。Bootstrap假設新的樣本都是從該經驗分布中得到的,即新的數據集服從該經驗分布,并且分布一直不變。如果每次采樣后不進行放回,那么這個經驗分布會一直改變。因此需要進行有放回的采樣。 ??顯然采樣后得到的新數據集中會包含同樣的樣本多次。如果重復采樣n次,那么原數據集中的樣本出現在新的數據集中的概率為1?1/e≈63.2%
,用另外一種講法,原數據集中有約2/3的數據會在新數據集中出現,并且有的會重復多次。 ??在對模型進行校驗時,可以使用新生成的數據集( bootstrapped dataset)對模型進行訓練,使用未被采樣的樣本集來對模型進行驗證。這種方式類似交叉校驗。 ??Jackknife翻譯成刀切法。Jackknife即從原始進行不放回采樣m(m
注意:模型驗證與測試不同
??在前面一直都是使用“驗證”這個詞作為模型訓練后需要進行的過程。而沒有使用“測試”這個詞。因為模型驗證與模型測試不同。 ??在原型設計階段中,需要進行模型選擇,即需要對多個候選模型在一個或多個驗證集上進行性能評價。當在模型訓練與驗證確定了合適的模型類型(如分類中是采用決策樹還是svm等)以及最優的超參數(如特征的個數)后,需要使用全部可利用的數據(包括前面對模型進行驗證的驗證集)對模型進行訓練,訓練出的模型便是最終的模型,即上線生產的模型。 ??模型測試則發生在模型的原型設計之后,即包含在上線階段又包含在離線監視(監測分布漂移 distribution drift)階段。 ??不要將訓練數據、驗證數據與測試數據相混淆。模型的訓練、驗證與測試應該使用不同的數據集,如果驗證數據集、測試數據集與訓練數據集有重疊部分,那么會導致模型的泛化能力差。 ??就在前一段時間,某隊在ImageNet(圖像識別最大數據庫)圖像識別測試挑戰賽競賽宣稱自己的效果擊敗了google和microsoft,圖像識別錯誤率低至4.58%,而microsoft為4.94%,谷歌為4.8%。但是最后查出他們違規了,按照測試的官方規定,參與者每周只能向服務器提交2次測試結果,而他們卻在5天內提交了40次結果。此外,ImageNet表示,他們還使用了30個不同的賬號,在過去6個月中提交了約200次測試結果。從本質上講,他們多次測試調優而得到了對測試數據集更好的擬合超參數和模型參數,因此模型的效果可能更好,但是可能會導致過擬合而使得模型的泛化能力差。
總結
??本節主要對模型離線評估與模型離線驗證進行講解。 * 在模型原型設計階段,需要進行模型選擇,包括超參數調優、模型訓練、模型驗證。 * Cross validation是一種生成訓練數據集與驗證數據集的機制;該方式在數據集較小時特別有用。 * Hyperparameter tuning是一種為模型選擇最優的超參數機制,需要使用交叉校驗來對超參數進行評估。 * Hold-out validation是另一種訓練數據集與驗證集的產生方式,它較簡單。當數據集較充分時使用。 * Bootstrapping與Jackknife是兩種不同的采樣方式,用來產生訓練集與驗證集。該方法可以為模型提供評價指標值方差與置信區間。
超參數調優(Hyperparameter Tuning)
??在機器學習領域,超參數調優是學習任務的先導步驟(meta),下面將對其進行介紹。
模型參數與超參數
??什么是模型的超參數,它與模型正常的參數有什么不同。機器學習從本質上來說是一個數學模型,它代表著數據的各個方面的聯系。 ??例如:在線性回歸模型中,使用一條線表示特征與目標之間的關系,用數學公式表示為 :
y=wTx

其中x
是特征向量,每個樣本使用一個特征向量進行表征,y
是一個數值變量,代表目標,w
則是每個特征的權值向量,代表著這條線的斜率。這個模型假設特征與目標之間是線性的。w
表示模型的參數,需要在模型的訓練階段進行學習更新,也就是說,模型訓練其實就是使用一種優化算法決定最優的模型參數來對數據進行擬合。 ??另外一種被稱為模型超參數。超參數的確定不是在模型的訓練階段。普通的線性回歸是沒有超參數的(除了特征的個數),而Ridge回歸與Lasso回歸都添加了正則項(Ridge嶺回歸加上L2正則項,Lasso回歸加上L1正則項),這些正則項都需要一個正則參數(regularization parameter)。如決策樹需要設置樹的深度和葉子數、支持向量機(SVM)需要設置一個分類錯誤的懲罰因子、帶核的SVM還需要設置核的參數(如RBF徑向基函數的寬度)等。
超參數的作用
?? 模型的超參數是用來干什么的呢?如正則化因子是來控制模型的能力,模型擬合數據的自由度(degrees of freedom)決定了模型的靈活度。合理的控制模型的能力能夠有效得防止過擬合現象。因此為了防止過擬合的發生,需要犧牲一些精度。因此合理的設置模型的超參數則非常重要。 ??另一種類型的模型超參數來自于模型的訓練階段。模型訓練是一個使損失函數(或代價函數,訓練階段的評價指標)最小化的過程,這過程會用到很多最優化技術與方法,使用的最優化方法中需要用到一些參數。如SGD( stochastic gradient descent)中,需要一個學習速率因子、初始點以及收斂閾值等。又如,隨機森林(Random Forests)和自助提升決策樹(Boosted decision trees)需要設置樹的個數的參數與正則化參數等等。這些超參數需要被合理地設置以找到一個好的模型。
超參數調優機制
??超參數設置的好壞對模型的評價指標值產生較大的影響。不同的數據集上面創建模型會有不同的最優超參數,因此對于不同的數據集需要各自調優。 ??如下圖,超參數的設置過程為:首先設置一個初始的超參數值,然后進行模型訓練,將模型的指標反饋都超參數調優機制中,調節超參數,繼續訓練模型,一直進行下去,若干次后得到一個目前最優的超參數值。最后使用該最優的超參數去訓練模型,并進行模型驗證。 ![](./屏幕快照 2015-09-28 下午3.07.45.png)
超參數調優算法
??從概念上講,超參數調優是一個最優化任務過程,就像模型訓練一樣。然而,這兩者之間相當的不同。在模型訓練中,使用一個稱為代價函數的數據公式為目標去進行對模型參數進行訓練調優。而在超參數調優中,無法使用一個形式化的公式為目標去進行調優,它就像一個黑盒子,需要使用模型訓練結束后的模型評價結果為指導去進行調優。這就是為什么超參數調優較為困難。下面是一些具體的超參數調優方法:
格搜索(Grid Search)
??顧名思義,格搜索便是將超參數的取值范圍劃分成一個個格子,然后對每一個格子所對應的值進行評估,選擇評估結果最好的格子所對應的超參數值。例如,對于決策樹葉子節點個數這一超參數,可以將值劃分為這些格子:10, 20, 30, …, 100, …;又如正則化因子這一超參數,一般使用指數值,那么可以劃分為:1e-5, 1e-4 1e-3, …, 1。有時可以進行猜測對格子進行搜索去獲得最優的超參數。如,當從第一個開始,發現效果較差,第二個好了一點,那么可以第三個可以取最后一個。格搜索較為簡單并且可以進行并行化。
隨機搜索(Random Search)
??在論文 “Random Search for Hyper Parameter Optimization” (Bergstra and Bengio)中,已經驗證了隨機搜索是一個簡單而有效的方法。它是格搜索的變種。相比于搜索整個格空間,隨機搜索只對隨機采樣的那些格進行計算,然后在這中間選擇一個最好的。因此隨機搜索比格搜索的代價低。隨機搜索有個缺點,即其可能找不到最優的點。但是前面的那篇論文已經證明,隨機采樣60個點的性能已經足夠好了。從概率的角度來說,對于任何的分布的樣本空間若存在最大值,那么隨機采樣60個點中的最大值位于整個樣本空間top5%的值的集合中的概率達到95%。證明如下: ??對于top%5的值,我們每次隨機采樣,得到top5%的值的概率為5%,沒有得到top5%的值的概率為(1-0.05),重復有放回地采樣n次,那么至少有一次得到top5的值這件事發生的概率若要超過95%,則:
1?(1?0.05)n>=0.95?n>=60

這表示我們只需要從所有候選格中隨機采樣60個格,便可以以95%的概率得到至少一個的top5%最優的格。因此隨機搜索60個格進行計算便可以以很高的概率得到top%5最優的格。當最優格以及近似最優格的集合較大,加上機器學習模型對超參數一個近似最優值與最優值不會太敏感,因此,隨機搜索算法便是有效的。由于隨機搜索簡單并且有效,一般是超參數調優的首選搜索算法。并且其容易并行化。
智能搜索(Smart Search)
??除了前面的兩種搜索算法,還可以利用智能搜索算法,但是相對于前面的兩種方法,智能搜索算法最大的缺點便是不能并行化。它的處理過程是一個序列,并只處理一部分候選點,然后對當前點進行評估,決定下一個點。智能搜索的目的是只對一部分點進行評估從而節省調優時間。 ??可以看出,智能搜索需要時間去計算下一個評估的點,于是相對于前面的方法,可能需要更多的時間。因此只有在對點進行評估所用的時間大于決定下一個需要評估的點的時間時才有意義。當然智能搜索算法也需要自己的超參數,因此也需要調優。有時好的智能搜索算法超參數可以確保智能搜索快于隨機搜索。 ??文章前面提到,超參數調優是一個困難的過程,因為它不能想模型參數調優那樣,給出一個形式化的數學函數,而對數學函數進行調優。因此很多優化算法,如牛頓優化算法、隨機梯度下降算法都不能使用。目前有超參數三個智能調優算法:derivative-free optimization, Bayesian optimization和random forest smart tuning。derivative-free優化算法采用啟發式來決定下一個計算的點;Bayesian和random forest優化算法都是創建一個響應函數曲面模型,由模型決定下一步需要計算的點。 ??Jasper Snoek等使用高斯過程對響應函數進行建模。Frank Hutter等使用回歸隨機森林來近似這個響應曲面。 Misha Bilenko等使用Nelder-Mead來進行超參數調優。
嵌套交叉校驗(Nested Cross-Validation)
??嵌套交叉校驗又稱為嵌套超參數調優。模型選擇與超參數調優的不同之處在于:模型選擇不僅包括對某個模型的參數進行調優(如決策樹的深度),并且包括對不同模型的選擇(如分類中,選擇決策樹還是SVM)。嵌套交叉校驗即在進行某個模型訓練后,需要對該模型進行交叉校驗,然后將結果反饋到超參數調優機制中,對超參數調優,并使用更新后的超參數繼續訓練模型,一直迭代下去,知道滿足一定的要求,同時對其它模型也需要如此進行訓練,最后在所有訓練好的模型選擇一個綜合各方面因素最優的模型。
A/B測試的陷阱
?? A/B測試(A/B Testing)是機器學習實踐中廣泛應用的一種方法。但是在應用該方法時,會遇到一些陷阱。下面便對相關問題進行討論。 ??在本文的前部分已經講述到,機器學習模型的評價分為離線評價與在線評價兩個階段。離線評價階段發生在模型原型設計階段,對不同的超參數、不同的特征集、不同模型進行評價,它是一個迭代的過程,使用選定的評價指標對每個迭代過程中生成的模型進行評價。一旦達到指定的迭代次數,則選擇所有迭代中最優的模型,作為最終模型并投入到生產環境中使用。而在線評價則是使用一些商業評價指標來對模型進行評價以及更新。而A/B測試則屬于在線測試。
什么是A/B測試
??A/B測試是目前在線測試中最主要的方法。該方法可以用來回答“新的模型比舊的模型更好嗎(模型)?”、“這個按鈕是使用黃色好一些還是藍色好(設計)”等等問題。在A/B測試中,與兩個部分:A和B,或控制/實驗(control and experiment),A代表舊模型(設計)的評價,B代表新的模型(設計)的評價,然后將它們進行對比,得到是否新的模型比舊模型更好。當然是由具體的機制來進行衡量。 ??該衡量方法便是統計假設檢驗(statistical hypothesis testing)。其用來回答“新的模型或設計是否對一些關鍵的評價指標有著大幅度的提升或者明顯的提升”。它包括兩個對立的假設:空假設(null hypothesis)與替代假設(alternate hypothesis)。前者表示“新的模型或設計沒有明顯的提升”,后者則表示“新的模型或設計有了明顯的提升”,“提升”具體反映在關鍵評價指標的平均值(mean value)等上面。 ??有很多書籍與網上資源對A/B測試有著詳細的描述,這里不再累贅。如 www.evanmiller.org,它對A/B測試進行了詳細的講解以及列舉了一些工具。簡而言之,A/B測試包括以下幾個步驟: * 隨機劃分成兩組A與B * 使用一些方法分別觀察兩組中的行為 * 計算一些統計指標 * 計算p-value * 最后輸出孰好孰壞 ??舉個最簡單的例子,在網頁設計中使用A/B測試。首先需要建立一個測試頁面(experiment page),這個頁面可能在標題字體,背景顏色,措辭等方面與原有頁面(control page)有所不同,然后將這兩個頁面以隨機的方式同時推送給所有瀏覽用戶。接下來分別統計兩個頁面的用戶轉化率,即可清晰的了解到兩種設計的優劣。 ??A/B測試雖然通俗易懂,但是要想正確的使用它則較為棘手。下面將介紹一些在使用A/B測試時可能會遇到的一些陷阱與問題,這些問題包括理論層面的和實踐層面的。
A/B測試的一些陷阱
實驗完全分離
??在A/B測試中,需要將用戶隨機分為兩組。一部分用戶使用舊的模型或設計(如瀏覽原來的網頁),另一部分用戶使用新的模型或設計(如瀏覽新設計的網頁)。那么需要保證experimentation組(使用新的模型或設計的組)的用戶的純凈度,什么意思呢? ??A/B測試中,劃分為完全獨立的,干凈的兩組是非常重要的。設想一下,在對網頁中的按鈕新樣式進行測試時,需要確保統一用戶自始自終是使用同一個按鈕設計,那么我們在對用戶進行隨機劃分時,就需要使用能夠唯一代表用戶的來進行劃分(即導流),如用戶ID,用戶sessions等。Kohavi等的KDD 2012論文表明一些使用舊設計的用戶再使用新的設計時會帶著某著偏見。
使用什么評價指標
??另一個重要的問題便是,在A/B測試中使用什么評價指標。因為A/B測試是在在線評價階段,因此使用的評價指標便是商業指標。但是商業指標有沒有離線階段那些評價指標那么容易計算。舉個例子,在搜索引擎中,一般對用戶的數目、用戶在結果站點的逗留時間、以及市場份額。在現實中,統計比較并不是那么容易,因此我們需要對獨立用戶每天訪問數、平均會話時間長度等這些能夠反映市場份額的指標進行計算,以便能夠對市場份額進行估計。并且一般短期指標并不與長期指標保持一致。 ??在機器學習過程中,一般會用到四種類型的評價指標,分別是:訓練評價指標(training metrics)、離線評價指標(驗證評價指標,offline evaluation metrics or validation metrics)、新生數據評價指標(live metrics)、商業指標(business metrics)。訓練評價指標是指模型優化的評價指標,即代價函數(目標函數或損失函數),如在線性回歸中使用平方誤差和、svm中分類平面幾何間隔最大化等。離線評價指標是指模型訓練完畢需要使用驗證數據集來對模型進行評價,即前面所提到的那些指標,如分類模型評價指標、回歸模型評價指標以及排序模型評價指標等。新生數據評價指標即使用模型上線后新生成的數據來評價模型,評價指標同離線評價指標,只是評價所用的數據不同。而商業指標即系統真正關心的最終指標,如轉化率、點擊率、PV訪問量、UV訪問量等。每個階段使用的評價指標不一樣,并且這些指標可能并不呈現線性相關,如在回歸模型中,隨著RMSE的下降,但是點擊率(click-through rates.)并沒有提高,詳細可以參見Kohavi‘s paper
多少改變才算是真正的改變?
??當確定了使用什么商業指標進行評價以及如何去計算這些指標時,接下來需要明確指標值提升了多少才算正在的提升,即多少的提升才可接受。這在某種程度上取決于實驗的觀察者數量。并且與問題2一樣,它并不是一個數據科學范疇的問題,而是一個商業問題。因此需要根據經驗挑選一個合適的值。
單面測試還是雙面測試(One-Sided or Two-Sided Test)?
??單面測試只能告訴你新的模型是否比基準的是否更好,而無法告訴你是否更糟。因此需要進行雙面測試,其不僅會告訴你新的模型是否會更好并且會告訴你是否更糟。是否更好與是否更糟需要進行分開對待。
多少的FP(False Positives)能夠忍受?
??比基準模型更好,但是實際上確不是。FP的代價取決于實際應用。如在醫藥中,FP意味著病人使用無效藥,這樣便會對患者的健康造成很大的威脅。又如在機器學習中,FP意味著會使用一個認為會更有效的但卻未更有效的模型來代替單前的模型。而FN意味著放棄了一個實際上會更有效的模型。 ??統計假設檢驗可以通過設定顯著性水平( the significance level)控制FP的概率,并通過測試的力(the power of the test.)度來控制FN的概率。 ??
需要多少觀察者?
??觀察者的數量由期望的統計功效(statistical power)部分決定。而統計功效在測試進行之前便需設定。一個常見的嘗試時運行測試直到觀察到一個重要的結果。這個方法是錯誤的。測試的力度是能夠正確識別那些正樣本。它能夠使用顯著性水平、A組的評價指標值與B組的評價指標值之差、觀察者的個數這些去形式化地表示。選擇合理的統計功效、顯著水平等。然后選擇每組中觀察者的數量。StitchFixEvan Miller’s website詳細地進行了介紹。 ??
評價指標是否滿足高斯分布
??A/B測試中絕大部分是使用T檢驗,但是T檢驗的所做出的假設前提并不是所有的評價指標都滿足的。一個好的方法便是去查看指標的分布與檢查T檢驗所做的假設是否有效。T檢驗假設是滿足高斯分布的,那么評價指標釋放滿足高斯分布呢?通常,使用中心極限定理可以得到任何獨立同分布并且具有期望與方差的隨機變量都收斂于高斯分布。不難得出,評價指標假設以下條件成立: * 指標值是采用平均值 * 指標值的分布是同一分布 * 指標值分布是對稱的 但是還是會有一些指標不滿足的,如點擊率是一個平均值,但是AUC卻是一個積分值。并且可能不服從同一分布,如在A/B組中的用戶種群不一樣。同時,也有可能不是對稱的。Kohavi等例舉了一些例子說明評價指標不服從高斯分布,在這些例子中,標準誤差不會隨著測試的進行而降低。比如那些計數評價指標服從負二項式分布。當這些假設不成立時,分布遍不再收斂于高斯分布。 ??
方差是否相等
??
p-value意味著什么
??
多模型,多參數
??
測試的時間需要多長
??
分布漂移問題
??
后面的改天補上……
原文地址:http://www.oreilly.com/data/free/evaluating-machine-learning-models.csp

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 227,572評論 6 531
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 98,071評論 3 414
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 175,409評論 0 373
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 62,569評論 1 307
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 71,360評論 6 404
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 54,895評論 1 321
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 42,979評論 3 440
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 42,123評論 0 286
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 48,643評論 1 333
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 40,559評論 3 354
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 42,742評論 1 369
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 38,250評論 5 356
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 43,981評論 3 346
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 34,363評論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 35,622評論 1 280
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 51,354評論 3 390
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 47,707評論 2 370

推薦閱讀更多精彩內容