机器学习——SVM之交叉验证对参数(C,gamma)进行优化以及选择
目錄
一、(C,gamma)簡介
二、交叉驗證
1、什么是交叉驗證?
2、參數優化方法
3、python實現交叉驗證cross_val_score(網格搜索算法GridSearchCV)
1)關鍵代碼
2)sklearn中的cross_val_score()函數參數
3)AX3D三維繪圖
4)ravel函數
5)完整代碼
?
?
前面寫了一篇關于參數(C,gamma)的文章,但是只是從感性上去說明了一下參數對模型和結果的影響,但沒有說明如何對參數(C,gamma)進行選擇。因此寫下這篇。
一、(C,gamma)簡介
對于SVM模型,最主要的參數就是C和gamma,C被稱為懲罰因子,越大說明對錯誤的容忍度越小,可能發生過擬合(overfitting),C太小可能會導致容錯率過高,這樣的模型就沒有意義了。
對于C和gamma參數的確定,一般是通過交叉驗證的方法來進行確定的,大概思路就是將C和gamma參數在一定地取值范圍內按照一定的步長(默認為1)進行取值組合,在不同(C,gamma)的組合下,將訓練集樣本均分成k組,一組作為驗證的數據樣本,其余k-1組則用來作為訓練的數據,每一組數據都輪流著作為驗證數據樣本,這樣在一組(C,gamma)組合下,就需要進行K次計算,把這K次計算的模型測試準確率score的均值作為這組(C,gamma)下模型的得分。這樣的話就能夠得到不同(C,gamma)組合下模型的得分,取得分最高的那組(C,gamma)即可,如果碰到有相同分的,一般考慮參數C,取C小的,因為在保證模型的準確率的情況下,C越小模型容錯率大,可以避免過擬合,若C也相同,則取先出現的那一組gamma
?
二、交叉驗證
1、什么是交叉驗證?
主要使用k-fold Cross Validation(記為k-CV)
就是將訓練樣本集進行均分,比如將訓練樣本集均分為k組,稱為k折,每次k-1折進行訓練,另一折用于驗證,每一組數據輪換作為驗證數據。這里驗證的是模型的識別率(accuracy)。在每一組(C,gamma)下對每一折數據進行輪換驗證,這就是交叉驗證,一般折數越多,越精確,但是計算的時間就會增加,需要在效率和精度之間進行權衡。
將C和gamma參數在一定地取值范圍內按照一定的步長(默認為1)進行取值組合,在不同(C,gamma)的組合下,將訓練集樣本均分成k組,一組作為驗證的數據樣本,其余k-1組則用來作為訓練的數據,每一組數據都輪流著作為驗證數據樣本,這樣在一組(C,gamma)組合下,就需要進行K次計算,把這K次計算的模型測試準確率score的均值作為這組(C,gamma)下模型的得分。這樣的話就能夠得到不同(C,gamma)組合下模型的得分,取得分最高的那組(C,gamma)即可,如果碰到有相同分的,一般考慮參數C,取C小的,因為在保證模型的準確率的情況下,C越小模型容錯率大,可以避免過擬合,若C也相同,則取先出現的那一組gamma
2、參數優化方法
可能很多人會有點懵,難道交叉驗證不是一個方法嗎?其實交叉驗證只是一種方案,而要去完成這個方案還需要方法,完成一個方案的方法有很多,不同的方法完成的效果也不一樣。同樣的道理參數的優化來說,優化算法有很多,如網格搜索算法、遺傳算法、粒子群算法、蟻群算法等,
對于交叉驗證來說,我們采取的是網格搜索算法,即在參數的一定的范圍內,按照指定的步長對不同的參數進行排列組合,將每一組參數組合進行測試,取性能指標最優的那一組參數作為最終參數的值。如本例中(C,gamma)組成了一個二維網格,再與性能指標識別率組成三維模型,這樣一來就可以實現參數的最優選擇啦!!!
《幾種常用交叉驗證(cross validation)方式的比較》
?
3、python實現交叉驗證cross_val_score(網格搜索算法GridSearchCV)
本例是一個兩特征三分類的問題,這里只涉及交叉驗證,沒有使用到網絡搜索算法,有興趣可以上網搜一下GridSearchCV
1)關鍵代碼
for C in range(1,10,1):for gamma in range(1,11,1):#獲得不同組合下的識別率,作為模型優劣評價的性能指標,這里需要注意的是,性能指標roc_auc,在本例中行不通,因為是多類問題,需要另外設置#獲得的識別率是交叉驗證后的平均值accuracy = cross_val_score(SVC(C=C/10,kernel='rbf',gamma=gamma/10),x,y.ravel(),cv=5,scoring='accuracy').mean()X.append(C/10)Y.append(gamma/10)Z.append(accuracy)M.append((C/10, gamma/10, accuracy))2)sklearn中的cross_val_score()函數參數
參考:《【Python】sklearn中的cross_val_score()函數參數》
sklearn 中的cross_val_score函數可以用來進行交叉驗證,因此十分常用,這里介紹這個函數的參數含義
sklearn.cross_validation.cross_val_score(estimator, X, y=None, scoring=None, cv=None, n_jobs=1, verbose=0, fit_params=None, pre_dispatch=‘2*n_jobs’)?
estimator:估計方法對象(分類器) X:數據特征(Features) y:數據標簽(Labels) soring:調用方法(包括accuracy、roc_auc、mean_squared_error等等) cv:幾折交叉驗證 n_jobs:同時工作的cpu個數(-1代表全部)3)AX3D三維繪圖
參考:《plot_surface(Axes3D)方法:繪制3D圖形》
3D 圖形需要的數據與等高線圖基本相同:X、Y 數據決定坐標點,Z 軸數據決定 X、Y 坐標點對應的高度。與等高線圖使用等高線來代表高度不同,3D 圖形將會以更直觀的形式來表示高度。
為了繪制 3D 圖形,需要調用 Axes3D 對象的 plot_surface() 方法來完成。
下面程序將使用與前面等高線圖相同的數據來繪制 3D 圖形,此時將看到程序會以更直觀的形式來顯示高度。
.................. fig = plt.figure() ax = Axes3D(fig) .................. # 繪制3D圖形 ax.plot_surface(X, Y, Z,rstride=1, # rstride(row)指定行的跨度cstride=1, # cstride(column)指定列的跨度cmap=plt.get_cmap('rainbow')) # 設置顏色映射 # 設置Z軸范圍 ax.set_zlim(-2, 2) # 設置標題 plt.title("3D圖") plt.show()#一定不要忘記這行 .................... import matplotlib.pyplot as plt import numpy as np from mpl_toolkits.mplot3d import Axes3D fig = plt.figure(figsize=(12, 8)) ax = Axes3D(fig) delta = 0.125 # 生成代表X軸數據的列表 x = np.arange(-3.0, 3.0, delta) # 生成代表Y軸數據的列表 y = np.arange(-2.0, 2.0, delta) # 對x、y數據執行網格化 X, Y = np.meshgrid(x, y) Z1 = np.exp(-X**2 - Y**2) Z2 = np.exp(-(X - 1)**2 - (Y - 1)**2) # 計算Z軸數據(高度數據) Z = (Z1 - Z2) * 2 # 繪制3D圖形 ax.plot_surface(X, Y, Z,rstride=1, # rstride(row)指定行的跨度cstride=1, # cstride(column)指定列的跨度cmap=plt.get_cmap('rainbow')) # 設置顏色映射 # 設置Z軸范圍 ax.set_zlim(-2, 2) # 設置標題 plt.title("3D圖") plt.show()?
4)ravel函數
將多維數組轉換成一維數組
可參考:《numpy——ravel()和flatten()》
column-vector y was passed when a 1d array was expected. Please change the shape of y to (n_samples, ), for example using ravel().return f(**kwargs) import numpy as np arr = np.array([[1, 2],[3, 4]]) arr.ravel() #降維默認行序優先,傳入參數‘F’表示列序優先 arr.ravel('F')##arr.ravel()=%s [1 2 3 4] ##arr.ravel('F')=%s [1 3 2 4]?
5)完整代碼
from sklearn.svm import SVC import numpy as np import sklearn import matplotlib.pyplot as plt from sklearn import preprocessing from sklearn.model_selection import cross_val_score from mpl_toolkits.mplot3d import Axes3D from sklearn.model_selection import GridSearchCV#define converts(字典) def Iris_label(s):it={b'Iris-setosa':0, b'Iris-versicolor':1, b'Iris-virginica':2 }return it[s]#1.讀取數據集 path='E:\PYTHON\machine_learning/Iris.data' data=np.loadtxt(path, dtype=float, delimiter=',', converters={4:Iris_label} ) #converters={4:Iris_label}中“4”指的是第5列:將第5列的str轉化為label(number)#2.劃分數據與標簽 x,y=np.split(data,indices_or_sections=(4,),axis=1) #x為數據,y為標簽,axis是分割的方向,1表示橫向,0表示縱向,默認為0 x=x[:,0:2] #為便于后邊畫圖顯示,只選取前兩維度。若不用畫圖,可選取前四列x[:,0:4]# x = preprocessing.scale(x)#預處理數據樣本X = [] Y = [] Z = [] M = []#定義列表,分別用于接受不同組合的C,gamma以及性能指標值 for C in range(1,10,1):for gamma in range(1,11,1):#獲得不同組合下的識別率,作為模型優劣評價的性能指標,這里需要注意的是,性能指標roc_auc,在本例中行不通,因為是多類問題,需要另外設置#獲得的識別率是交叉驗證后的平均值accuracy = cross_val_score(SVC(C=C/10,kernel='rbf',gamma=gamma/10),x,y.ravel(),cv=5,scoring='accuracy').mean()X.append(C/10)Y.append(gamma/10)Z.append(accuracy)M.append((C/10, gamma/10, accuracy)) print(M)#5、以C,gamma,auc作為三個坐標變量繪圖#將列表轉換成數組 X = np.array(X).reshape(9,10) Y = np.array(Y).reshape(9,10) Z = np.array(Z).reshape(9,10)#繪制三維圖形 fig = plt.figure() ax = Axes3D(fig) ax.plot_surface(X,Y,Z,rstride=1,cstride=1,cmap=plt.get_cmap('rainbow')) # ax.scatter(Y,X,Z,c='r') plt.xlabel('Gamma') plt.ylabel('C') plt.title('gamma_C_auc') plt.show()繪制圖像如下,圖中紅色部分則為識別率最高的地方,取該處的(C,gamma)作為參數進行模型訓練。
至于具體怎么去得到最優的參數,我們可以在內層循環中再嵌入一個判斷語句,大概思路為:先假設k = 0,m=0,n=0,將每次循環得到的accuracy與k做比較,若accuracy大于k,則將accuracy的值賦給k,同時將C賦值給m,將gamma賦值給n,最后就能夠得到最大的accuracy時的參數,當然也有可能出現accuracy相同時的情況,這時候就判斷C的大小,取C小的那組,同理gamma也是如此!!!這樣我們就找到了最優參數C,gamma啦
?
總結
以上是生活随笔為你收集整理的机器学习——SVM之交叉验证对参数(C,gamma)进行优化以及选择的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: GAN 的推导、证明与实现。
- 下一篇: 用python计算工程量_基于Pytho