【目標檢測】一、初始的R-CNN與SVM
1.流程
2.數學概念
SVM(Support Vector Machines),主要想找到分離一批資料的超平面,約定是,找到距離這個超平面最近的點做距離該點最遠的線(/面)。
支援向量(support vecotr)就是離超平面最近的點,SVM由此命名。
而規劃超平面涉及到核(Kernal)函式概念,最終計算SVM會是解決不等式約束問題,這裡面就有多種方式。
(原始的SVM僅用於二分類,分類標籤按計算需求確定,可能是0和1,或者是-1和1,以此區分兩個類別。多種分類需要動刀函式距離)
對於一個二維平面來說,如果能用一條直線區分出兩批資料,那麼如何確定這條直線呢(可能會有多條),
SVM原則是找到兩批資料中點距離目標線最近的點,距離最大的解。這聽起來有很多個未知數
已知點A,假設超平面表示式(目標函式)為 ,那麼點A對y的距離(推導過程讓人腦閉,有需要再深究):
這個yi是取-1和1的標籤值,注,yi的i不同書寫在了不同位置(上標或下標),但都是表示標籤。
為了下文計算方便,把分子拎出來,為了掉絕對值,此處新增變數yi(表示標籤值,i = 1,2,3,..n,表示第幾個資料)[2],
yi取-1或1,以使分子結果不變,
設定下式為函式距離(或稱為函式間隔),可以表示點到超平面的距離遠近。
目標是找到函式距離最小值,
下一步是求距離超平面最近的點對超平面的距離最大化之解:
優化問題,分成兩個整體來處理,
已知要求的函式間隔最小,那麼有:
整理一下,
又 不影響margin取值,此處可令其為1,(?[2]筆者並不太明白),
求||w||最小值等價於||w||²/2的最小值,為了求導方便,上式可轉化為:
為了求解線性可分支援向量機的最優化問題,將它作為原始最優化問題,
應用拉格朗日對偶性,通過求解對偶問題(dual problem)得到原始問題(primal problem)的最優解,這就是線性可分支援向量機的對偶演算法,
這樣做的優點:一是對偶問題往往更容易求解;二是自然引入核函式,進而推廣到非線性分類問題。----《統計學習方法》
關於如何求解拉格朗日此處不敘述,詳見[2][3],
拉格朗日乘數法式子:
省略化簡,得到約束:
注,尖括號表示向量內積(也即點積)。
由於此時假設資料100%線性可分,然而真實資料並不都是那麼“乾淨”,此處引入鬆弛變數(slack variable),以允許有些資料點處於分隔面錯誤的一側,約束條件變為:C≥α ≥ 0 ,
如何求解,傳統地有二次規劃求解(quadratic solver),但是這個計算量大,John Platt釋出了一個叫SMO(Sequential Minimal Optimization,序列最小優化)的演算法以減少計算。
簡化的SMO虛擬碼:
建立一個α向量並將其初始化為0的向量
當迭代次數小於最小迭代次數時(外迴圈):
對資料集中的每個資料向量(內迴圈):
如果該資料向量可以被優化:
隨機選擇另外一個數據向量
同時優化這兩個向量
如何這兩個向量不能被同時優化,退出內迴圈
如果所有向量都沒被優化,增加迭代數目,繼續下一次迴圈
核(kernel)函式
如果一批資料並沒有呈現明顯的直線劃分規律,例如呈現環分佈的劃分規律,
那麼求解這個低緯度的非線性問題,最好就把它轉化成高緯度的線性問題,前者轉化到後者,這個對映過程用核函式滿足。
因為SVM的向量都是內積表示,這裡面把內積運算替換成核函式的方式,就叫做核技巧(kernel trick)或核變電(kernel substation)。
徑向基核函式(Radial Basis Function),是某種沿徑向對稱的標量函式,是一個常用的度量兩個向量距離的核函式。
例如,線性問題,是 ,非線性問題,假設核函式取徑向基函式的高斯版本:
(?)其中,σ是使用者定義的用於確定到達率(reach)或者說函式值跌落到0的速度引數。
def kernelTrans(X, A, kTup): m,n = shape(X) K = mat(zeros((m, 1))) if kTup[0] == ’lin’ : K = X*A.T elif kTup[0] == ‘rbf’ : for j in range(m): deltaRow = X[j, :] – A # 公式 K[j] = deltaRow*deltaRow.T # 平方 K = exp(K / (-1*kTup[1]**2)) # 元素間的除法 else : raise NameError(‘That Kernel is not recognizaed~~’) return K class optStruct: def __init__(self, dataMatIn, classLabels, C, toler, kTup): self.X = dataMatIn …. self.m = shape(dataMatIn)[0] self.K = mat(zeros((self.m, self.m))) for i in range(self.m): self.K[:,i] = kernalTrans(self.X, self.X[i, :], kTup)
SVM用於數值型資料,視覺化分割超平面,其主要求解在於兩個變數的調優,幾乎所有分類問題都可以用SVM,
原始的SVM是一個二分類器,應對多類問題需要調整SVM,
但其核函式的選擇,以及核函式裡自定義變數的影響,使得這個最優解需要大量訓練。
=======================================================
資料:
[1] https://baike.baidu.com/item/拉格朗日乘數法/8550443?fromtitle=拉格朗日乘子法
[2] https://zhuanlan.zhihu.com/p/146515617
[3] https://blog.csdn.net/m0_37687753/article/details/80964472?spm=1001.2014.3001.5501
Peter Harrington著《機器學習實戰》
https://blog.csdn.net/m0_37687753/article/details/80964487
https://blog.csdn.net/laobai1015/article/details/82763033
https://baike.baidu.com/item/函式間隔/23224467?fr=aladdin
3.應用程式碼
現實中沒有使用到,暫且擱置。