網(wǎng)站建設(shè)行業(yè)發(fā)展洛陽網(wǎng)站建設(shè)

?作者簡介:人工智能專業(yè)本科在讀,喜歡計(jì)算機(jī)與編程,寫博客記錄自己的學(xué)習(xí)歷程。
🍎個人主頁:小嗷犬的個人主頁
🍊個人網(wǎng)站:小嗷犬的技術(shù)小站
🥭個人信條:為天地立心,為生民立命,為往圣繼絕學(xué),為萬世開太平。
本文目錄
- imblearn 簡介
- imblearn 安裝
- 欠采樣方法
- ClusterCentroids
- EditedNearestNeighbours
- CondensedNearestNeighbour
- AllKNN
- InstanceHardnessThreshold
- 過采樣方法
- SMOTE
- SMOTE-NC
- SMOTEN
- ADASYN
- BorderlineSMOTE
- KMeansSMOTE
- SVMSMOTE
- 組合采樣方法
- SMOTETomek
- SMOTEENN
- imblearn 庫使用示例
- 導(dǎo)入庫
- 查看原始數(shù)據(jù)分布
- 采樣后的數(shù)據(jù)分布
- 不同采樣方法的可視化對比
imblearn 簡介
imblearn(全名為 imbalanced-learn )是一個用于處理不平衡數(shù)據(jù)集的 Python 庫。在許多實(shí)際情況中,數(shù)據(jù)集中的類別分布可能是不均衡的,這意味著某些類別的樣本數(shù)量遠(yuǎn)遠(yuǎn)超過其他類別。這可能會導(dǎo)致在訓(xùn)練機(jī)器學(xué)習(xí)模型時出現(xiàn)問題,因?yàn)槟P涂赡軙蛴趯W(xué)習(xí)多數(shù)類別。
imblearn 庫提供了一系列處理不平衡數(shù)據(jù)集的方法,包括:
- 欠采樣方法:減少多數(shù)類別的樣本以使其與少數(shù)類別相匹配。
- 過采樣方法:通過生成合成樣本來增加少數(shù)類別的樣本數(shù)量,使其與多數(shù)類別相匹配。
- 組合采樣方法:結(jié)合了欠采樣和過采樣的技術(shù),以獲得更好的平衡。
imblearn 庫包含了許多常用的不平衡數(shù)據(jù)處理算法,例如SMOTE(Synthetic Minority Over-sampling Technique)、Tomek Links、RandomUnderSampler、RandomOverSampler 等等。
這個庫對于處理各種類型的不平衡數(shù)據(jù)問題非常有用,可以提升在這類數(shù)據(jù)上訓(xùn)練模型的性能。
imblearn 安裝
imblearn 庫可以通過 pip 安裝:
pip install imblearn
欠采樣方法
欠采樣方法通過減少多數(shù)類別的樣本數(shù)量來平衡數(shù)據(jù)集。這些方法通常用于處理大型數(shù)據(jù)集,因?yàn)樗鼈兛梢詼p少數(shù)據(jù)集的大小。
下面我們將介紹 imblearn 庫中的一些常用欠采樣方法。
ClusterCentroids
ClusterCentroids 是一種欠采樣方法,它通過聚類算法來減少多數(shù)類別的樣本數(shù)量。它通過將多數(shù)類別的樣本聚類為多個簇,然后對每個簇選擇其中心作為新的樣本來實(shí)現(xiàn)。
具體來說,ClusterCentroids 采取以下步驟:
- 將多數(shù)類別的樣本分成幾個簇(clusters)。
- 對于每個簇,選擇其中心點(diǎn)作為代表樣本。
- 最終的訓(xùn)練集將包含所有少數(shù)類別樣本以及選定的多數(shù)類別樣本中心點(diǎn)。
EditedNearestNeighbours
EditedNearestNeighbours (簡稱 ENN)是一種欠采樣方法,它通過刪除多數(shù)類別中的異常值來減少多數(shù)類別的樣本數(shù)量。它通過以下步驟實(shí)現(xiàn):
- 對于每一個多數(shù)類別的樣本,找到它的 k 個最近鄰居(根據(jù)指定的距離度量)。
- 如果多數(shù)類別的樣本的大多數(shù)最近鄰居屬于與它不同的類別(即多數(shù)類別樣本的大多數(shù)鄰居屬于少數(shù)類別),則將該樣本移除。
CondensedNearestNeighbour
CondensedNearestNeighbour 是一種欠采樣方法,它通過選擇多數(shù)類別樣本的子集來減少多數(shù)類別的樣本數(shù)量。它通過以下步驟實(shí)現(xiàn):
- 將少數(shù)類別的樣本全部保留在訓(xùn)練集中。
- 逐一考察多數(shù)類別的樣本。對于每一個多數(shù)類別的樣本,找到它的k個最近鄰居(根據(jù)指定的距離度量)。
- 如果多數(shù)類別的樣本能夠被少數(shù)類別樣本所代表,即該多數(shù)類別樣本的最近鄰居中存在少數(shù)類別樣本,則將該多數(shù)類別樣本移除。
AllKNN
AllKNN 是一種欠采樣方法,它在執(zhí)行時會多次應(yīng)用 ENN(Edited Nearest Neighbours)算法,并在每次迭代時逐步增加最近鄰的數(shù)量。
AllKNN 通過多次應(yīng)用 ENN,并逐步增加最近鄰的數(shù)量,可以更加徹底地清除位于類別邊界附近的噪聲樣本。
InstanceHardnessThreshold
InstanceHardnessThreshold 是一種欠采樣方法,它通過計(jì)算每個樣本的難度分?jǐn)?shù)來減少多數(shù)類別的樣本數(shù)量。它通過以下步驟實(shí)現(xiàn):
- 計(jì)算多數(shù)類別中每個樣本的難度分?jǐn)?shù)。
- 剔除難度分?jǐn)?shù)低于指定閾值的樣本。
- 將剩余樣本與少數(shù)類別的樣本組合成新的訓(xùn)練集。
過采樣方法
過采樣方法通過生成合成樣本來增加少數(shù)類別的樣本數(shù)量,使其與多數(shù)類別相匹配。這些方法通常用于處理小型數(shù)據(jù)集,因?yàn)樗鼈兛梢栽黾訑?shù)據(jù)集的大小。
下面我們將介紹 imblearn 庫中的一些常用過采樣方法。
SMOTE
SMOTE(Synthetic Minority Over-sampling Technique)是一種過采樣方法,它通過生成合成樣本來增加少數(shù)類別的樣本數(shù)量,使其與多數(shù)類別相匹配。
SMOTE 的原理基于對少數(shù)類樣本的插值。具體而言,它首先隨機(jī)選擇一個少數(shù)類樣本作為起始點(diǎn),然后從該樣本的近鄰中隨機(jī)選擇一個樣本作為參考點(diǎn)。然后,SMOTE 通過在這兩個樣本之間的線段上生成新的合成樣本來增加數(shù)據(jù)集的樣本數(shù)量。
SMOTE-NC
SMOTE-NC(SMOTE for Nominal and Continuous features)是一種用于處理同時包含數(shù)值和分類特征的數(shù)據(jù)集的過采樣方法。它是對傳統(tǒng)的 SMOTE 算法的擴(kuò)展,能夠處理同時存在數(shù)值和分類特征的情況,但不適用于僅包含分類特征的數(shù)據(jù)集。
SMOTE-NC 的原理與 SMOTE 類似,但在生成合成樣本時有所不同。它的生成過程如下:
- 對于選定的起始點(diǎn)和參考點(diǎn),計(jì)算它們之間的差距,得到一個向量。
- 將連續(xù)特征(數(shù)值特征)的差距乘以一個隨機(jī)數(shù),得到新樣本的位置。這一步與傳統(tǒng)的 SMOTE 相同。
- 對于分類特征,隨機(jī)選擇起始點(diǎn)或參考點(diǎn)的特征值作為新合成樣本的特征值。
- 對于連續(xù)特征和分類特征,分別使用插值和隨機(jī)選擇的方式來生成新樣本的特征值。
通過這種方式,SMOTE-NC 能夠處理同時包含數(shù)值和分類特征的數(shù)據(jù)集,并生成新的合成樣本來增加少數(shù)類樣本的數(shù)量。這樣可以在平衡數(shù)據(jù)集的同時保持?jǐn)?shù)值和分類特征的一致性。
SMOTEN
SMOTEN(Synthetic Minority Over-sampling Technique for Nominal)是一種專門針對分類特征的過采樣方法,用于解決類別不平衡問題。它是對 SMOTE 算法的擴(kuò)展,適用于僅包含分類特征的數(shù)據(jù)集。
SMOTEN 的原理與 SMOTE 類似,但在生成合成樣本時有所不同。它的生成過程如下:
- 對于選定的起始點(diǎn)和參考點(diǎn),計(jì)算它們之間的差距,得到一個向量。
- 對于每個分類特征,統(tǒng)計(jì)起始點(diǎn)和參考點(diǎn)之間相應(yīng)特征的唯一值(類別)的頻率。
- 根據(jù)特征的頻率,確定新樣本的位置。具體而言,對于每個分類特征,隨機(jī)選擇一個起始點(diǎn)或參考點(diǎn)的類別,并在該類別中隨機(jī)選擇一個值作為新合成樣本的特征值。
- 對于連續(xù)特征,采用傳統(tǒng)的 SMOTE 方式,通過在差距向量上乘以一個隨機(jī)數(shù),確定新樣本的位置,并使用插值來生成新樣本的特征值。
ADASYN
ADASYN(Adaptive Synthetic)是一種基于自適應(yīng)合成的過采樣算法。它與 SMOTE 方法相似,但根據(jù)類別的局部分布估計(jì)生成不同數(shù)量的樣本。
ADASYN 根據(jù)樣本之間的差距,計(jì)算每個樣本的密度因子。密度因子表示該樣本周圍少數(shù)類樣本的密度。較低的密度因子表示該樣本所屬的區(qū)域缺乏少數(shù)類樣本,而較高的密度因子表示該樣本周圍有更多的少數(shù)類樣本。
BorderlineSMOTE
BorderlineSMOTE(邊界 SMOTE)是一種過采樣算法,是對原始 SMOTE 算法的改進(jìn)和擴(kuò)展。它能夠檢測并利用邊界樣本生成新的合成樣本,以解決類別不平衡問題。
BorderlineSMOTE 在 SMOTE 算法的基礎(chǔ)上進(jìn)行了改進(jìn),通過識別邊界樣本來更有針對性地生成新的合成樣本。邊界樣本是指那些位于多數(shù)類樣本和少數(shù)類樣本之間的樣本,它們往往是難以分類的樣本。通過識別并處理這些邊界樣本,BorderlineSMOTE 能夠提高分類器對難以分類樣本的識別能力。
KMeansSMOTE
KMeansSMOTE 的關(guān)鍵在于使用 KMeans 聚類將數(shù)據(jù)樣本劃分為不同的簇,并通過識別邊界樣本來有針對性地進(jìn)行合成樣本的生成。這種方法可以提高合成樣本的多樣性和真實(shí)性,因?yàn)樗鼉H在邊界樣本周圍進(jìn)行過采樣,而不是在整個少數(shù)類樣本集上進(jìn)行。
SVMSMOTE
SVMSMOTE 是一種基于 SMOTE 算法的變體,其特點(diǎn)是利用支持向量機(jī)(SVM)算法來檢測用于生成新的合成樣本的樣本。通過將數(shù)據(jù)集中的少數(shù)類樣本劃分為支持向量和非支持向量,SVMSMOTE 能夠更準(zhǔn)確地選擇樣本進(jìn)行合成。對于每個少數(shù)類支持向量,它選擇其最近鄰中的一個作為參考點(diǎn),并通過計(jì)算其與參考點(diǎn)之間的差距來生成新的合成樣本。
組合采樣方法
組合采樣方法結(jié)合了欠采樣和過采樣的技術(shù),以獲得更好的平衡。
下面我們將介紹 imblearn 庫中的一些常用組合采樣方法。
SMOTETomek
SMOTETomek 是一種組合采樣方法,它結(jié)合了 SMOTE 和 Tomek Links 算法。Tomek Links 是一種欠采樣方法,它通過刪除多數(shù)類別樣本和少數(shù)類別樣本之間的邊界樣本來減少多數(shù)類別的樣本數(shù)量。
SMOTETomek 通過結(jié)合 SMOTE 和 Tomek Links 算法,能夠同時處理多數(shù)類別和少數(shù)類別的樣本,以獲得更好的平衡。
SMOTEENN
SMOTEENN 是一種組合采樣方法,它結(jié)合了 SMOTE 和 ENN 算法。
相比于 SMOTETomek,由于 SMOTEENN 結(jié)合了 ENN 算法,因此它能夠更容易地清除位于類別邊界附近的噪聲樣本。
imblearn 庫使用示例
下面我們將通過一個示例來演示 imblearn 庫的使用。
導(dǎo)入庫
首先,我們需要導(dǎo)入一些需要用到的庫:
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as snsfrom sklearn.datasets import load_breast_cancer # sklearn 乳腺癌數(shù)據(jù)集
from imblearn.under_sampling import ClusterCentroids, EditedNearestNeighbours
from imblearn.over_sampling import SMOTE, ADASYN
from imblearn.combine import SMOTEENN, SMOTETomek
查看原始數(shù)據(jù)分布
我們使用 sklearn 自帶的乳腺癌數(shù)據(jù)集作為示例數(shù)據(jù)集。首先,我們導(dǎo)入數(shù)據(jù)集,并查看數(shù)據(jù)集的基本信息:
data = load_breast_cancer()X = data.data
y = data.targetprint(f"類別為 0 的樣本數(shù): {X[y == 0].shape[0]}, 類別為 1 的樣本數(shù): {X[y == 1].shape[0]}")sns.set_style("darkgrid")
sns.scatterplot(data=data, x=X[:, 0], y=X[:, 1], hue=y)
plt.xlabel(f"{data.feature_names[0]}")
plt.ylabel(f"{data.feature_names[1]}")
plt.title("Original")
plt.show()
輸出結(jié)果如下:
類別為 0 的樣本數(shù): 212, 類別為 1 的樣本數(shù): 357
采樣后的數(shù)據(jù)分布
接下來,我們使用 imblearn 庫中的一些采樣方法來處理數(shù)據(jù)集,以獲得更好的平衡。
data = load_breast_cancer()X = data.data
y = data.targetsampler1 = ClusterCentroids(random_state=0)
sampler2 = EditedNearestNeighbours()
sampler3 = SMOTE(random_state=0)
sampler4 = ADASYN(random_state=0)
sampler5 = SMOTEENN(random_state=0)
sampler6 = SMOTETomek(random_state=0)X1, y1 = sampler1.fit_resample(X, y)
X2, y2 = sampler2.fit_resample(X, y)
X3, y3 = sampler3.fit_resample(X, y)
X4, y4 = sampler4.fit_resample(X, y)
X5, y5 = sampler5.fit_resample(X, y)
X6, y6 = sampler6.fit_resample(X, y)print(f"ClusterCentroids: 類別為 0 的樣本數(shù): {X1[y1 == 0].shape[0]}, 類別為 1 的樣本數(shù): {X1[y1 == 1].shape[0]}"
)
print(f"EditedNearestNeighbours: 類別為 0 的樣本數(shù): {X2[y2 == 0].shape[0]}, 類別為 1 的樣本數(shù): {X2[y2 == 1].shape[0]}"
)
print(f"SMOTE: 類別為 0 的樣本數(shù): {X3[y3 == 0].shape[0]}, 類別為 1 的樣本數(shù): {X3[y3 == 1].shape[0]}"
)
print(f"ADASYN: 類別為 0 的樣本數(shù): {X4[y4 == 0].shape[0]}, 類別為 1 的樣本數(shù): {X4[y4 == 1].shape[0]}"
)
print(f"SMOTEENN: 類別為 0 的樣本數(shù): {X5[y5 == 0].shape[0]}, 類別為 1 的樣本數(shù): {X5[y5 == 1].shape[0]}"
)
print(f"SMOTETomek: 類別為 0 的樣本數(shù): {X6[y6 == 0].shape[0]}, 類別為 1 的樣本數(shù): {X6[y6 == 1].shape[0]}"
)
輸出結(jié)果如下:
ClusterCentroids: 類別為 0 的樣本數(shù): 212, 類別為 1 的樣本數(shù): 212
EditedNearestNeighbours: 類別為 0 的樣本數(shù): 212, 類別為 1 的樣本數(shù): 320
SMOTE: 類別為 0 的樣本數(shù): 357, 類別為 1 的樣本數(shù): 357
ADASYN: 類別為 0 的樣本數(shù): 358, 類別為 1 的樣本數(shù): 357
SMOTEENN: 類別為 0 的樣本數(shù): 304, 類別為 1 的樣本數(shù): 313
SMOTETomek: 類別為 0 的樣本數(shù): 349, 類別為 1 的樣本數(shù): 349
不同采樣方法的可視化對比
下面我們將使用 matplotlib 和 seaborn 庫來可視化不同采樣方法的效果。
sns.set_style("darkgrid")
plt.figure(figsize=(9, 18))plt.subplot(4, 2, 1)
sns.scatterplot(data=data, x=X1[:, 0], y=X1[:, 1], hue=y1)
plt.title("ClusterCentroids")plt.subplot(4, 2, 2)
sns.scatterplot(data=data, x=X2[:, 0], y=X2[:, 1], hue=y2)
plt.title("EditedNearestNeighbours")plt.subplot(4, 2, 3)
sns.scatterplot(data=data, x=X3[:, 0], y=X3[:, 1], hue=y3)
plt.title("SMOTE")plt.subplot(4, 2, 4)
sns.scatterplot(data=data, x=X4[:, 0], y=X4[:, 1], hue=y4)
plt.title("ADASYN")plt.subplot(4, 2, 5)
sns.scatterplot(data=data, x=X5[:, 0], y=X5[:, 1], hue=y5)
plt.title("SMOTEENN")plt.subplot(4, 2, 6)
sns.scatterplot(data=data, x=X6[:, 0], y=X6[:, 1], hue=y6)
plt.title("SMOTETomek")plt.show()
對比結(jié)果如下: