數據抽樣及樣本不均衡處理


一、數據抽樣

抽樣的組織形式有:

(1)簡單隨機抽樣:按等概率原則直接從總體中抽取樣本。該方法適用於個體分布均勻的場景。

(2)分層抽樣:先對總體分組,再從每組中隨機抽樣。該方法適用於帶有分類邏輯屬性的數據。

(3)等距抽樣:先將總體中的每個個體按順序編號,計算抽樣間隔,然后按照固定間隔抽取個體。該方法適用於個體分布均勻或呈現明顯的均勻分布規律,無明顯趨勢或周期性規律的數據。

(4)整群抽樣:將總體分為若干部分,(每個部分稱為一群),以群為單位隨機抽樣,跟其他三種方法的不同在於該方法抽取的是群,而不是數據個體。

#讀入數據
1
import numpy as np 2 import pandas as pd 3 import random 4 df=pd.read_csv(r'E:\data analysis\test\test2.csv') 5 print(df.head(3))

      id  var0  var1  var2  var3  var4  var5  var6  var7  var8
0  16144     1    14    13     5    25     5    45     6     1
1  16145     1    15    14     6    26     1     6     7     1
2  16146     1    16    15     7    27     2     1     8    
#簡單隨機抽樣
1
df_srs=pd.DataFrame.sample(df,n=20) 2 print(df_srs.head(3)) 3 print(len(df_srs))

    id  var0  var1  var2  var3  var4  var5  var6  var7  var8
99   17090     1    75     6    19    23     9     2     4     5
30   17021     1     6     5    19    55    16     8     9     2
107  17098     0     1    14     1    31    17     2    12     5

20
 #等距抽樣
1
sample_count=20 2 df_count=df.shape[0] 3 width=df_count/sample_count 4 df_is=[] 5 i=0 6 while i*width<=df_count-1: 7 sample=df.ix[i*width] 8 df_is.append(sample) 9 i+=1 10 df_is=pd.DataFrame(df_is) 11 print(df_is.head(3)) 12 print(len(df_is))

   id  var0  var1  var2  var3  var4  var5  var6  var7  var8
0   16144     1    14    13     5    25     5    45     6     1
10  17001     1    24    23    15    35     4     1     2     1
20  17011     1    34    33     9    45     6    11     1     2

20
#分層抽樣
1
each_sample_count=10 2 label_unique=np.unique(df['var0']) 3 df_ss=pd.DataFrame(np.zeros((1,len(df.columns))),columns=df.columns,dtype=int) 4 for label in label_unique: 5 sample=pd.DataFrame.sample(df[df['var0']==label],each_sample_count) 6 df_ss=pd.concat([df_ss,sample]) 7 df_ss=df_ss[1:] 8 print(df_ss) 9 print(len(df_ss))

        id  var0  var1  var2  var3  var4  var5  var6  var7  var8
161  17152     0    37    14    15    18     5    10    31     8
102  17093     0    78     9     2    26    12     5     7     5
183  18020     0    59    36    10    17     5     7     2     9
131  17122     0     7     6    25    23     9    15     1     7
112  17103     0     1     3     6     4    22     7    17     6
170  18007     0    46    23    24     4     7     2    40     9
126  17117     0     2     1    20    18     4    10    12     6
196  18033     0    72     9    11     7     4     6     3    10
199  18036     0    75    12    14     4     7     3     6    10
158  17149     0    34    11    12    15     8     7    28     8
45   17036     1    21     6     5    70     9    23    11     3
48   17039     1    24     9     8    73     1    26    14     3
4    16148     1    18    17     9    29     4     3    10     1
57   17048     1    33     1    17     6     3     4     7     3
96   17087     1    72     3    16    20     6     6     1     5
76   17067     1    52    20     1     4    12    11     2     4
19   17010     1    33    32     8    44     5    10     7     1
67   17058     1    43    11    27    16     3     2     6     4
11   17002     1    25    24     3    36     5     2     3     1
26   17017     1     2     1    15    51    12     4     5     2

20

 #整群抽樣
1
label_unique=np.unique(df['var8']) 2 sample_label=random.sample(list(label_unique),2) 3 df_cs=pd.DataFrame(np.zeros((1,len(df.columns))),columns=df.columns,dtype=int) 4 print(sample_label) 5 for label in sample_label: 6 sample=df[df['var8']==label] 7 df_cs=pd.concat([df_cs,sample]) 8 df_cs=df_cs[1:] 9 print(df_cs) 10 print(len(df_cs))

[10, 2]
        id  var0  var1  var2  var3  var4  var5  var6  var7  var8
187  18024     0    63     2     2    21     4    11     6    10
188  18025     0    64     1     3    22     5    12     7    10
189  18026     0    65     2     4     4     6    13     8    10
......
38   17029     1    14    13    27    63     2    16     4     2
39   17030     1    15     2    28    64     3    17     5     2
40   17031     1    16     1     3    65     4    18     6     2
41   17032     1    17     2     1    66     5    19     7     2
42   17033     1    18     3     2    67     6    20     8     2

36

 

二、解決樣本不均衡的問題

樣本不均衡是指不同類別的樣本量差異很大。

解決方法:

1、過抽樣:增加分類中少數類樣本的數量,最簡單的方法就是復制少數類樣本形成多條記錄。改進的過抽樣方法是在少數類中加入隨機噪聲、干擾數據或通過一定規則產生新的合成樣本。例如SMOTE算法。過抽樣方法應用極廣泛。

     欠抽樣:減少分類中多數類樣本的數量,最簡單的方法就是隨機去掉一些多數樣本。

2、通過正負樣本的懲罰權重來解決不均衡:對於分類中不同樣本數量的類別分別賦予不同權重(一般小樣本量類別權重大,大樣本量類別權重小),然后進行計算和建模,例SVM。

3、通過組合/集成方法解決權重不均衡:從分類中的大樣本量中隨機抽取數據來與小樣本合並構成訓練集。

#導入數據,查看類別數量
1
import numpy as np 2 import pandas as pd 3 from imblearn.over_sampling import SMOTE 4 df=pd.read_csv(r'E:\data analysis\test\test3.csv') 5 print(df.head(3)) 6 df_groupby=df.groupby('var8').count() 7 print(df_groupby)

      id  var1  var2  var3  var4  var5  var6  var7  var8
0  16144    14    13     5    25     5    45     6     1
1  16145    15    14     6    26     1     6     7     1
2  16146    16    15     7    27     2     1     8     1


       id  var1  var2  var3  var4  var5  var6  var7
var8                                               
0     174   174   174   174   174   174   174   174
1      26    26    26    26    26    26    26    26
       id  var1  var2  var3  var4  var5  var6  var7

 

#使用SMOTE方法進行過抽樣
1
x=df.ix[:,:-1] #id~var7 2 y=df.ix[:,-1] #var8 即標簽列 3 model_smote=SMOTE() 4 x_smote,y_smote=model_smote.fit_sample(x,y) 5 x_smote=pd.DataFrame(x_smote,columns=['id','var1','var2','var3','var4','var5','var6','var7']) 6 y_smote=pd.DataFrame(y_smote,columns=['var8']) 7 smote_xy=pd.concat([x_smote,y_smote],axis=1) 8 groupby_smote_xy=smote_xy.groupby('var8').count() 9 print(groupby_smote_xy)

var8                                               
0     174   174   174   174   174   174   174   174
1     174   174   174   174   174   174   174   174

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM