您好,登錄后才能下訂單哦!
R語言中數據不平衡如何解決?相信很多沒有經驗的人對此束手無策,為此本文總結了問題出現的原因和解決方法,通過這篇文章希望你能解決這個問題。
開發工具:RStudio
R:3.5.2
相關包:dplyr、ROSE、DMwR
首先我們要知道的第一個問題就是“什么是數據不平衡”,從字面意思上進行解釋就是數據分布不均勻。在我們做有監督學習的時候,數據中有一個類的比例遠大于其他類,或者有一個類的比值遠小于其他類時,我們就可以認為這個數據存在數據不平衡問題。
那么這樣的一個問題會對我們后續的分析工作帶來怎樣的影響呢?我舉個簡單的例子,或許大家就明白了。
假設我們現在需要訓練一個模型來分辨人群中那個人是恐怖分子。那么現在給到我們1萬個人員的數據,在做分析之前其實我們就很清楚,一群人中恐怖分子的比例肯定是要遠小于普通人的比例的。
那么假如在這1萬個人中只有一個是恐怖分子,那么恐怖分子與正常人的比例就是 9999 : 1 。
那么如果我們不進行任何處理就直接進行有監督學習的話,那么模型只需要將所有人數據都分類為正常人,模型的準確率就能達到99.99%。而這樣的模型顯然是沒有意義的。
因為基本上說有可能存在的恐怖分子的特征基本都被模型給忽略了,這也就說明了為什么要處理數據不平衡問題。
以下是幾種比較常見的處理數據不平衡的方法:
1、欠采樣法(Undersampling)
2、過采樣法(Oversampling)
3、人工數據合成法(Synthetic Data Generation)
4、代價敏感學習法(Cose Sensitive Learning)
【注】:本文主要以實現為主,因此不對上述方法進行過多的講解。
在處理數據之前,我們先看一下需要處理的數據分布的情況。
load("C:/Users/User/Desktop/data.RData") table(data$classification) prop.table(table(data$classification))
> table(data$classification)
-8 1 2 3 4 5
12 104 497 1158 4817 1410
> prop.table(table(data$classification))
-8 1 2 3 4 5
0.001500375 0.013003251 0.062140535 0.144786197 0.602275569 0.176294074
1、 欠采樣
######### 方法一 ######### library(ROSE) # 由于是多分類問題,我們先提取數據中比例最大的類和比例最小的類 # 進行平衡(轉化為二分類問題) test <- data[which(data$classification == -8 | data$classification == 4),] # 將分類結果轉化為因子型(不然會報錯) test$classification <- as.factor(test$classification) # 進行欠采樣 # 其中 method = "under" 表示采用的方法為“欠采樣” # N = 40 表示最終整個數據集的數量 # seed 隨機種子,為了保留對樣本的追蹤 under <- ovun.sample(classification ~ ., test, method = "under", N = 40, seed = 1)$data # 查看結果 table(under$classification)
> table(under$classification)
4 -8
28 12
######### 方法二 ######### library(dplyr) # 由于是多分類問題,我們先提取數據中比例最大的類和比例最小的類 # 進行平衡(轉化為二分類問題) test <- data[which(data$classification == -8 | data$classification == 4),] # 提取大比例類 test1 <- test[which(test$classification == 4),] # 將大比例類的數量降為12個 down <- sample_n(test1, 12, replace = TRUE) # 將欠采樣后的類進行合并 down <- rbind(test[which(test$classification == -8), ],down) table(down$classification)
> table(down$classification)
-8 4
12 12
【注】:欠采樣是無放回的采樣。
2、 過采樣
######### 方法一 ######### library(ROSE) test <- data[which(data$classification == -8 | data$classification == 4),] test$classification <- as.factor(test$classification) # 實現上大致與欠采樣相同,只有類型 method 改成了 "over",同時沒有限制總數量 under <- ovun.sample(classification ~ ., test, method = "over", seed = 1)$data table(under$classification)
> table(under$classification)
4 -8
4817 4785
######### 方法二 ######### library(dplyr) test <- data[which(data$classification == -8 | data$classification == 4),] # 提取小比例類 test1 <- test[which(test$classification == -8),] # 將小比例類的數量降為4817個(與大比例類相同) # 這里使用的過采樣方法是隨機復制小比例類中的數據,將其擴充到指定數量 down <- sample_n(test1, 4817, replace = TRUE) down <- rbind(test[which(test$classification == 4), ],down) table(down$classification)
> table(down$classification)
-8 4
4817 4817
3、人工數據合成法(Synthetic Data Generation)
######### 方法一 ######### library(ROSE) # 由于是多分類問題,我們先提取數據中比例最大的類和比例最小的類 # 進行平衡(轉化為二分類問題) test <- data[which(data$classification == -8 | data$classification == 4),] # 將分類結果轉化為因子型(不然會報錯) test$classification <- as.factor(test$classification) # ROSE提供了ROSE()函數來合成人工數據 rose <- ROSE(classification ~ ., test, seed = 1)$data # 查看結果 table(rose$classification)
> table(rose$classification)
4 -8
2483 2346
######### 方法二 ######### library(DMwR) test <- data[which(data$classification == -8 | data$classification == 4),] test$classification <- as.factor(test$classification) # perc.over: 如 perc.over = n,小比例類的個數變為 (n/100)a + a 個數據(a為小比例類原始數量) # perc.under: 如 perc.under = m,大比例類的個數變為((nm)/100)a個 # 因此本次案例中,小比例類的個數變為(3500/100)*12 + 12 = 432個 # 大比例類的個數變為((3500*300)/100^2)*12 = 1260個 down <- SMOTE(classification ~ ., test, perc.over = 3500, perc.under = 300) table(down$classification)
> table(down$classification)
-8 4
432 1260
【注】:相較于前兩種方法而言,人工合成法既不會像過采樣容易導致過擬合問題,也不會出現欠采樣大量丟失信息的問題。
4、代價敏感學習法(Cose Sensitive Learning)
R語言是用于統計分析、繪圖的語言和操作環境,屬于GNU系統的一個自由、免費、源代碼開放的軟件,它是一個用于統計計算和統計制圖的優秀工具。
看完上述內容,你們掌握R語言中數據不平衡如何解決的方法了嗎?如果還想學到更多技能或想了解更多相關內容,歡迎關注億速云行業資訊頻道,感謝各位的閱讀!
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。