OpenCV 4.13.0
開源計算機視覺庫 (Open Source Computer Vision)
正在載入...
正在搜尋...
未找到匹配項
機器學習概述

訓練資料

在機器學習演算法中存在訓練資料的概念。訓練資料包括幾個組成部分:

  • 一組訓練樣本。每個訓練樣本都是一個值向量(在計算機視覺中有時被稱為特徵向量)。通常所有向量具有相同數量的元件(特徵);OpenCV ml 模組假定如此。每個特徵可以是排序的(即,其值是浮點數,可以相互比較並嚴格排序,即可以排序)或分類的(即,其值屬於一個固定的值集,可以是整數、字串等)。
  • 對應於樣本的可選響應集。沒有響應的訓練資料用於無監督學習演算法,這些演算法根據不同樣本之間的距離來學習所提供資料的結構。有響應的訓練資料用於監督學習演算法,這些演算法學習將樣本對映到響應的函式。通常響應是標量值,如果是迴歸問題,則為有序的;如果是分類問題,則為分類的(在這種情況下,響應通常被稱為“標籤”)。一些演算法,最值得注意的是神經網路,不僅可以處理標量響應,還可以處理多維或向量響應。
  • 另一個可選元件是缺失測量值的掩碼。大多數演算法要求所有訓練樣本中的所有元件都有效,但其他一些演算法(例如決策樹)可以處理缺失測量值的情況。
  • 對於分類問題,使用者可能希望為不同的類別賦予不同的權重。例如,這在以下情況下很有用:
    • 使用者希望將預測準確性轉向較低的誤報率或較高的命中率。
    • 使用者希望補償來自不同類別的訓練樣本數量顯著不同的情況。
  • 除此之外,如果使用者希望演算法特別關注某些訓練樣本並相應地調整訓練模型,則可以為每個訓練樣本賦予一個權重。
  • 此外,使用者可能希望不一次性使用所有訓練資料,而是使用其中的一部分,例如透過交叉驗證過程進行引數最佳化。

如您所見,訓練資料可能具有相當複雜的結構;此外,它可能非常大和/或無法完全獲取,因此需要對這個概念進行抽象。在 OpenCV ml 中,cv::ml::TrainData 類就是為此而設。

另請參閱
cv::ml::TrainData

正態貝葉斯分類器

這個簡單的分類模型假設來自每個類別的特徵向量呈正態分佈(儘管不一定是獨立分佈)。因此,整個資料分佈函式被假定為高斯混合,每個類別一個分量。演算法使用訓練資料來估計每個類別的均值向量和協方差矩陣,然後使用它們進行預測。

另請參閱
cv::ml::NormalBayesClassifier

K近鄰

該演算法快取所有訓練樣本,並透過分析樣本的最近鄰居(數量為 K)來預測新樣本的響應,使用投票、計算加權和等方法。該方法有時被稱為“按示例學習”,因為它在預測時尋找與給定向量最接近且已知響應的特徵向量。

另請參閱
cv::ml::KNearest

支援向量機

最初,支援向量機 (SVM) 是一種用於構建最優二元(2 類)分類器的技術。後來該技術擴充套件到迴歸和聚類問題。SVM 是基於核方法的特例。它使用核函式將特徵向量對映到更高維空間,並在此空間中構建一個最優線性判別函式或一個最優超平面,使其與訓練資料擬合。在 SVM 的情況下,核函式沒有明確定義。相反,需要定義超空間中任意兩點之間的距離。

解決方案是最優的,這意味著分離超平面與來自兩個類別的最近特徵向量之間的裕度(在 2 類分類器的情況下)最大化。最接近超平面的特徵向量被稱為 支援向量,這意味著其他向量的位置不影響超平面(決策函式)。

OpenCV 中的 SVM 實現基於 [52]

另請參閱
cv::ml::SVM

使用 SVM 進行預測

應使用 StatModel::predict(samples, results, flags)。傳遞 flags=StatModel::RAW_OUTPUT 以獲取來自 SVM 的原始響應(在迴歸、1 類或 2 類分類問題中)。

決策樹

本節討論的 ML 類實現了 [42] 中描述的分類和迴歸樹演算法。

cv::ml::DTrees 類表示單個決策樹或決策樹集合。它也是 RTrees 和 Boost 的基類。

決策樹是二叉樹(其中每個非葉節點有兩個子節點)。它可用於分類或迴歸。對於分類,每個樹葉都標有類別標籤;多個葉子可能具有相同的標籤。對於迴歸,也為每個樹葉分配一個常數,因此逼近函式是分段常數。

另請參閱
cv::ml::DTrees

使用決策樹進行預測

為了到達葉節點並獲得輸入特徵向量的響應,預測過程從根節點開始。從每個非葉節點開始,根據儲存在觀察節點中的某個變數的值,過程向左(選擇左子節點作為下一個觀察節點)或向右。可能的變數如下:

  • 有序變數。 變數值與也儲存在節點中的閾值進行比較。如果值小於閾值,則過程向左。否則,向右。例如,如果重量小於 1 公斤,則過程向左,否則向右。
  • 分類變數。 測試離散變數值是否屬於某個值子集(也儲存在節點中),該值子集來自變數可以採用的有限值集。如果是,則過程向左。否則,向右。例如,如果顏色是綠色或紅色,則向左,否則向右。

因此,在每個節點中,使用一對實體(variable_index, decision_rule (threshold/subset))。這對實體被稱為 split(在 variable_index 變數上的拆分)。一旦到達葉節點,分配給該節點的值將用作預測過程的輸出。

有時,輸入向量的某些特徵會缺失(例如,在黑暗中很難確定物體顏色),預測過程可能會卡在某個節點中(在上述示例中,如果節點按顏色拆分)。為了避免這種情況,決策樹使用所謂的 代理拆分(surrogate splits)。也就是說,除了最佳的“主要”拆分之外,每個樹節點還可以按一個或多個其他變數拆分,這些變數的結果幾乎相同。

訓練決策樹

樹是遞迴構建的,從根節點開始。所有訓練資料(特徵向量和響應)用於拆分根節點。在每個節點中,根據某些標準找到最佳決策規則(最佳“主要”拆分)。在機器學習中,基尼“純度”標準用於分類,平方誤差和用於迴歸。然後,如有必要,找到代理拆分。它們在訓練資料上模仿主要拆分的結果。所有資料都使用主要和代理拆分(如在預測過程中所做的那樣)在左子節點和右子節點之間劃分。然後,該過程遞迴地拆分左節點和右節點。在每個節點中,遞迴過程可能會在以下情況之一停止(即停止進一步拆分節點):

  • 構建的樹分支深度已達到指定的閾值。
  • 節點中的訓練樣本數量小於指定的閾值,此時進一步拆分節點在統計上沒有代表性。
  • 節點中的所有樣本屬於同一類別,或者在迴歸情況下,變化太小。
  • 找到的最佳拆分與隨機選擇相比沒有明顯的改進。

構建樹後,如有必要,可以使用交叉驗證過程進行剪枝。也就是說,可能導致模型過擬合的某些樹分支被剪掉。通常,此過程僅應用於獨立決策樹。樹集合通常會構建足夠小的樹,並使用自己的保護機制來防止過擬合。

變數重要性

除了作為決策樹的明顯用途的預測之外,樹還可以用於各種資料分析。構建的決策樹演算法的一個關鍵特性是能夠計算每個變數的重要性(相對決定能力)。例如,在垃圾郵件過濾器中,它使用訊息中出現的單詞集作為特徵向量,變數重要性評級可用於確定最“垃圾郵件指示性”的單詞,從而有助於保持字典大小合理。

每個變數的重要性是根據樹中該變數的所有拆分(主要和代理拆分)計算的。因此,為了正確計算變數重要性,必須在訓練引數中啟用代理拆分,即使沒有缺失資料。

提升(Boosting)

常見的機器學習任務是監督學習。在監督學習中,目標是學習輸入 \(x\) 和輸出 \(y\) 之間的函式關係 \(F: y = F(x)\)。預測定性輸出稱為 分類,而預測定量輸出稱為 迴歸

提升是一種強大的學習概念,它為監督分類學習任務提供瞭解決方案。它結合了許多“弱”分類器的效能,以產生一個強大的委員會 [279]。弱分類器只需要比隨機猜測好即可,因此可以非常簡單且計算成本低廉。然而,它們中的許多透過巧妙地結合結果,形成一個強大的分類器,其效能通常優於大多數“整體”強分類器,例如 SVM 和神經網路。

決策樹是提升方案中最常用的弱分類器。通常,每棵樹只有一個拆分節點的最簡單決策樹(稱為 stumps)就足夠了。

提升模型基於 \(N\) 個訓練示例 \({(x_i,y_i)}1N\),其中 \(x_i \in{R^K}\) 且 \(y_i \in{-1, +1}\)。\(x_i\) 是一個 \(K\) 分量向量。每個分量編碼與手頭學習任務相關的特徵。所需的二類輸出被編碼為 -1 和 +1。

已知的提升變體包括離散 Adaboost、實值 AdaBoost、LogitBoost 和 Gentle AdaBoost [99]。它們在整體結構上非常相似。因此,本章僅關注標準的二類離散 AdaBoost 演算法,概述如下。最初,為每個樣本分配相同的權重(步驟 2)。然後,使用加權訓練資料訓練一個弱分類器 \(f_{m(x)}\)(步驟 3a)。計算其加權訓練誤差和縮放因子 \(c_m\)(步驟 3b)。對於被錯誤分類的訓練樣本,權重增加(步驟 3c)。然後對所有權重進行歸一化,並繼續尋找下一個弱分類器的過程,再進行 \(M\) -1 次。最終分類器 \(F(x)\) 是單個弱分類器加權和的符號(步驟 4)。

二類離散 AdaBoost 演算法

  • 設定 \(N\) 個示例 \({(x_i,y_i)}1N\),其中 \(x_i \in{R^K}, y_i \in{-1, +1}\)。
  • 分配權重為 \(w_i = 1/N, i = 1,...,N\)。
  • 重複 \(m = 1,2,...,M\)
    • 使用訓練資料上的權重 \(w_i\) 擬合分類器 \(f_m(x) \in{-1,1}\)。
    • 計算 \(err_m = E_w [1_{(y \neq f_m(x))}], c_m = log((1 - err_m)/err_m)\)。
    • 設定 \(w_i \Leftarrow w_i exp[c_m 1_{(y_i \neq f_m(x_i))}], i = 1,2,...,N,\) 並重新歸一化,使得 \(\Sigma i w_i = 1\)。
  • 使用公式 \(\textrm{sign} (\Sigma m = 1M c_m f_m(x))\) 對新樣本 x 進行分類。
注意
與經典提升方法類似,當前的實現僅支援二類分類器。對於 M > 2 類,有 AdaBoost.MH 演算法(在 [99] 中描述),它將問題簡化為二類問題,但訓練集要大得多。

為了減少提升模型的計算時間而又不大幅降低準確性,可以使用影響修剪技術。隨著訓練演算法的進行和整合中的樹數量增加,越來越多的訓練樣本被正確分類並具有越來越高的置信度,因此這些樣本在後續迭代中獲得的權重越來越小。相對權重非常低的示例對弱分類器訓練的影響很小。因此,在弱分類器訓練期間可以排除這些示例,而不會對誘導分類器產生太大影響。此過程由 weight_trim_rate 引數控制。在弱分類器訓練中,僅使用總權重質量中總結分數 weight_trim_rate 的示例。請注意,所有 訓練示例的權重在每次訓練迭代中都會重新計算。在特定迭代中刪除的示例可能會在後續學習某些弱分類器時再次使用 [99]

另請參閱
cv::ml::Boost

使用提升進行預測

應使用 StatModel::predict(samples, results, flags)。傳遞 flags=StatModel::RAW_OUTPUT 以獲取來自 Boost 分類器的原始總和。

隨機樹

隨機樹由 Leo Breiman 和 Adele Cutler 引入:http://www.stat.berkeley.edu/users/breiman/RandomForests/。該演算法可以處理分類和迴歸問題。隨機樹是樹預測器的一個集合(整合),在本節中進一步稱為 森林(該術語也由 L. Breiman 引入)。分類工作方式如下:隨機樹分類器接受輸入特徵向量,使用森林中的每棵樹對其進行分類,並輸出獲得多數“投票”的類別標籤。在迴歸的情況下,分類器響應是森林中所有樹的響應的平均值。

所有樹都使用相同的引數進行訓練,但訓練集不同。這些集合是使用載入程式從原始訓練集中生成的:對於每個訓練集,您隨機選擇與原始集合中相同數量的向量(=N)。向量是帶替換抽樣的。也就是說,有些向量會出現不止一次,有些則會缺失。在每棵訓練樹的每個節點中,並非所有變數都用於找到最佳拆分,而是使用它們的隨機子集。對於每個節點,都會生成一個新的子集。然而,它的大小對於所有節點和所有樹都是固定的。它是一個訓練引數,預設設定為 \(\sqrt{number\_of\_variables}\)。構建的樹都不會被剪枝。

在隨機樹中,不需要任何準確性估計程式,例如交叉驗證或載入程式,也不需要單獨的測試集來估計訓練誤差。誤差是在訓練期間內部估計的。當使用帶替換抽樣繪製當前樹的訓練集時,一些向量會被遺漏(所謂的 oob(out-of-bag)資料)。oob 資料的大小約為 N/3。分類誤差使用此 oob 資料進行估計,如下所示:

  • 使用第 i 棵樹對相對於第 i 棵樹是 oob 的每個向量進行預測。
  • 所有樹都訓練完成後,對於曾經是 oob 的每個向量,找到它的類別-贏家(在向量是 oob 的樹中獲得多數投票的類別),並將其與基本事實響應進行比較。
  • 計算分類誤差估計,即錯誤分類的 oob 向量數量與原始資料中所有向量數量之比。在迴歸的情況下,oob 誤差計算為 oob 向量差異的平方誤差除以向量總數。

有關隨機樹的使用示例,請參閱 OpenCV 發行版中的 letter_recog.cpp 示例。

另請參閱
cv::ml::RTrees

參考文獻

期望最大化

期望最大化(EM)演算法估計高斯混合分佈形式的多元機率密度函式的引數,其中指定了混合物的數量。

考慮從高斯混合中提取的 d 維歐幾里得空間中的 N 個特徵向量集 { \(x_1, x_2,...,x_{N}\) }

\[p(x;a_k,S_k, \pi _k) = \sum _{k=1}^{m} \pi _kp_k(x), \quad \pi _k \geq 0, \quad \sum _{k=1}^{m} \pi _k=1,\]

\[p_k(x)= \varphi (x;a_k,S_k)= \frac{1}{(2\pi)^{d/2}\mid{S_k}\mid^{1/2}} exp \left \{ - \frac{1}{2} (x-a_k)^TS_k^{-1}(x-a_k) \right \} ,\]

其中 \(m\) 是混合物的數量,\(p_k\) 是均值為 \(a_k\)、協方差矩陣為 \(S_k\) 的正態分佈密度,\(\pi_k\) 是第 k 個混合物的權重。給定混合物的數量 \(M\) 和樣本 \(x_i\), \(i=1..N\),該演算法找到所有混合物引數的最大似然估計 (MLE),即 \(a_k\), \(S_k\) 和 \(\pi_k\)

\[L(x, \theta )=logp(x, \theta )= \sum _{i=1}^{N}log \left ( \sum _{k=1}^{m} \pi _kp_k(x) \right ) \to \max _{ \theta \in \Theta },\]

\[\Theta = \left \{ (a_k,S_k, \pi _k): a_k \in \mathbbm{R} ^d,S_k=S_k^T>0,S_k \in \mathbbm{R} ^{d \times d}, \pi _k \geq 0, \sum _{k=1}^{m} \pi _k=1 \right \} .\]

EM 演算法是一個迭代過程。每次迭代包括兩個步驟。在第一步(期望步或 E 步)中,您使用當前可用的混合物引數估計值找到樣本 i 屬於混合物 k 的機率 \(p_{i,k}\)(在下面的公式中表示為 \(\alpha_{i,k}\))

\[\alpha _{ki} = \frac{\pi_k\varphi(x;a_k,S_k)}{\sum\limits_{j=1}^{m}\pi_j\varphi(x;a_j,S_j)} .\]

在第二步(最大化步或 M 步)中,使用計算出的機率來最佳化混合物引數估計值

\[\pi _k= \frac{1}{N} \sum _{i=1}^{N} \alpha _{ki}, \quad a_k= \frac{\sum\limits_{i=1}^{N}\alpha_{ki}x_i}{\sum\limits_{i=1}^{N}\alpha_{ki}} , \quad S_k= \frac{\sum\limits_{i=1}^{N}\alpha_{ki}(x_i-a_k)(x_i-a_k)^T}{\sum\limits_{i=1}^{N}\alpha_{ki}}\]

或者,當可以提供 \(p_{i,k}\) 的初始值時,演算法可以從 M 步開始。當 \(p_{i,k}\) 未知時,另一種替代方法是使用更簡單的聚類演算法對輸入樣本進行預聚類,從而獲得初始 \(p_{i,k}\)。通常(包括機器學習),k-means 演算法用於此目的。

EM 演算法的主要問題之一是需要估計大量的引數。大多數引數位於協方差矩陣中,每個矩陣有 \(d \times d\) 個元素,其中 \(d\) 是特徵空間維度。然而,在許多實際問題中,協方差矩陣接近對角矩陣,甚至接近 \(\mu_k*I\),其中 \(I\) 是單位矩陣,\(\mu_k\) 是依賴於混合物的“尺度”引數。因此,一個穩健的計算方案可以從對協方差矩陣施加更嚴格的約束開始,然後使用估計的引數作為輸入進行約束較少的最佳化問題(通常對角協方差矩陣已經是一個足夠好的近似)。

另請參閱
cv::ml::EM

參考文獻

  • Bilmes98 J. A. Bilmes. A Gentle Tutorial of the EM Algorithm and its Application to Parameter Estimation for Gaussian Mixture and Hidden Markov Models. Technical Report TR-97-021, International Computer Science Institute and Computer Science Division, University of California at Berkeley, April 1998.

神經網路

ML 實現了前饋人工神經網路,更具體地說是多層感知器(MLP),這是最常用的神經網路型別。MLP 由輸入層、輸出層和一個或多個隱藏層組成。MLP 的每一層都包含一個或多個神經元,與前一層和下一層的神經元定向連線。下面的示例表示一個 3 層感知器,具有三個輸入、兩個輸出,以及包含五個神經元的隱藏層

影像

MLP 中的所有神經元都是相似的。每個神經元都有多個輸入連結(它將前一層中多個神經元的輸出值作為輸入)和多個輸出連結(它將響應傳遞給下一層中多個神經元)。從前一層檢索的值與某些權重相加,每個神經元都有單獨的權重,加上偏差項。使用啟用函式 \(f\) 對和進行轉換,該函式對於不同的神經元也可能不同。

影像

換句話說,給定第 \(n\) 層的輸出 \(x_j\),第 \(n+1\) 層的輸出 \(y_i\) 計算如下:

\[u_i = \sum _j (w^{n+1}_{i,j}*x_j) + w^{n+1}_{i,bias}\]

\[y_i = f(u_i)\]

可以使用不同的啟用函式。ML 實現了三個標準函式:

影像

在 ML 中,所有神經元都具有相同的啟用函式,具有相同的自由引數(\(\alpha, \beta\)),這些引數由使用者指定,並且不會被訓練演算法更改。

因此,整個訓練好的網路工作方式如下:

  1. 將特徵向量作為輸入。向量大小等於輸入層的大小。
  2. 將值作為輸入傳遞給第一個隱藏層。
  3. 使用權重和啟用函式計算隱藏層的輸出。
  4. 將輸出進一步傳遞到下游,直到計算出輸出層。

因此,要計算網路,您需要知道所有權重 \(w^{n+1)}_{i,j}\)。權重由訓練演算法計算。該演算法接受一個訓練集、多個具有相應輸出向量的輸入向量,並迭代調整權重,使網路能夠對提供的輸入向量給出所需的響應。

網路規模(隱藏層數量及其大小)越大,網路的潛在靈活性就越大。訓練集上的誤差可以任意減小。但同時,學習到的網路也會“學習”訓練集中存在的噪聲,因此在網路規模達到限制後,測試集上的誤差通常開始增加。此外,較大的網路訓練時間比小的網路長得多,因此對資料進行預處理是合理的,使用 cv::PCA 或類似技術,並在僅包含基本特徵的較小網路上進行訓練。

MLP 的另一個特點是無法直接處理分類資料。然而,有一種變通方法。如果輸入或輸出層中的某個特徵(在 \(n>2\) 的 n 類分類器的情況下)是分類的,並且可以採用 \(M>2\) 個不同的值,則將其表示為 M 個元素的二元組是有意義的,其中第 i 個元素當且僅當該特徵等於 M 個可能值中的第 i 個值時為 1。這增加了輸入/輸出層的大小,但加快了訓練演算法的收斂速度,同時使此類變數的“模糊”值成為可能,即機率元組而不是固定值。

ML 實現了兩種用於訓練 MLP 的演算法。第一種演算法是經典的隨機序列反向傳播演算法。第二種(預設)演算法是批次 RPROP 演算法。

另請參閱
cv::ml::ANN_MLP

邏輯迴歸

ML 實現了邏輯迴歸,這是一種機率分類技術。邏輯迴歸是一種二元分類演算法,與支援向量機 (SVM) 密切相關。與 SVM 一樣,邏輯迴歸可以擴充套件到處理多類分類問題,例如數字識別(即從給定影像中識別 0,1, 2, 3,... 等數字)。此版本的邏輯迴歸支援二元和多類分類(對於多類分類,它會建立多個 2 類分類器)。為了訓練邏輯迴歸分類器,使用了批次梯度下降和迷你批次梯度下降演算法(參見 http://en.wikipedia.org/wiki/Gradient_descent_optimization)。邏輯迴歸是一種判別分類器(有關更多詳細資訊,請參見 http://www.cs.cmu.edu/~tom/NewChapters.html)。邏輯迴歸在 LogisticRegression 中作為 C++ 類實現。

在邏輯迴歸中,我們嘗試最佳化訓練引數 \(\theta\),使得假設 \(0 \leq h_\theta(x) \leq 1\) 成立。我們有 \(h_\theta(x) = g(h_\theta(x))\) 和 \(g(z) = \frac{1}{1+e^{-z}}\) 作為邏輯或 S 形函式。“邏輯”在邏輯迴歸中指的是這個函式。對於類別 0 和 1 的二元分類問題給定的資料,如果 \(h_\theta(x) \geq 0.5\),則可以確定給定資料例項屬於類別 1,如果 \(h_\theta(x) < 0.5\),則屬於類別 0。

在邏輯迴歸中,選擇正確的引數對於減少訓練誤差和確保高訓練準確性至關重要

  • 學習率可以使用 setLearningRate 方法設定。它決定了我們接近解的速度。它是一個正實數。
  • LogisticRegression 支援批次梯度下降和迷你批次梯度下降等最佳化演算法。重要的是要提及這些最佳化演算法必須執行的迭代次數。迭代次數可以使用 setIterations 設定。這個引數可以看作是採取的步驟數,學習率指定了這是一大步還是小步。這個引數和前一個引數共同定義了我們到達可能解的速度。
  • 為了補償過擬合,執行正則化,可以使用 setRegularization 啟用。可以透過將 regularization kinds 之一傳遞給此方法來指定要執行的正則化型別。
  • 邏輯迴歸實現提供了兩種訓練方法的選擇:批次梯度下降或迷你批次梯度下降。要指定此項,請使用 LogisticRegression::BATCHLogisticRegression::MINI_BATCH 呼叫 setTrainMethod。如果訓練方法設定為 MINI_BATCH,則迷你批次的大小必須是正整數,使用 setMiniBatchSize 設定。

邏輯迴歸分類器的一組訓練引數示例可以按如下方式初始化:

Ptr<LogisticRegression> lr1 = LogisticRegression::create();
lr1->setLearningRate(0.001);
lr1->setIterations(10);
lr1->setRegularization(LogisticRegression::REG_L2);
lr1->setTrainMethod(LogisticRegression::BATCH);
lr1->setMiniBatchSize(1);
另請參閱
cv::ml::LogisticRegression