- 原文地址:Support Vector Machine (SVM) Tutorial
- 原文作者:Abhishek Ghose
- 譯文出自:掘金翻譯計劃
- 本文永久連結:github.com/xitu/gold-m…
- 譯者:zhmhhu
- 校對者:TrWestdoor, 1992chenlu
支援向量機(SVM)教程
從例子中學習 SVM
在 Statsbot 團隊釋出關於時間序列異常檢測的帖子之後,許多讀者要求我們告訴他們有關支援向量機的方法。現在是時候在不涉及複雜數學知識的情況下向您介紹SVM,並分享有用的庫和資源以幫助您入門了。
如果您已經使用機器學習來執行分類,您可能聽說過支援向量機(SVM)。50 多年前被引入,它們隨著時間的推移而發展,並且已經適應了各種其他問題,如迴歸分析、異常值分析和排名。
SVM 是許多機器學習從業者的最佳工具。在[24]7,我們也使用它們來解決各種問題。
在這篇文章中,我們將嘗試深入瞭解 SVM 的工作原理。我會專注於建立直覺而並不追求嚴謹。這基本上意味著我們將盡可能多地跳過數學並建立起對工作原理的直覺理解。
分類問題
假設您的大學提供機器學習(ML)課程。課程導師觀察到,如果學生擅長數學或統計學,他們將獲得最大的收益。隨著時間的推移,他們記錄了這些科目的入學學生的分數。此外,對於其中的每一個學生,他們都有一個描述他們在 ML 課程中表現“好”或“差”的標籤。
現在,他們想要確定數學和統計學分數與 ML 課程中的表現之間的關係。也許,根據他們發現的內容,他們希望指定入學課程的先決條件。
情況會怎麼樣呢? 讓我們從表示他們擁有的資料開始。我們可以繪製一個二維圖,其中一個軸代表數學分數,而另一個代表統計分數。具有特定分數的學生在圖表上顯示為一個點。
點的顏色——綠色或紅色——代表他在 ML 課程中的表現:分別為“好”或“差”。
繪出來的圖有可能是這樣的:
當學生要求報名時,我們的教師會要求她提供她的數學和統計學分數。根據他們已有的資料,他們會對 ML 課程中的表現做出有根據的的猜測。
我們本質上想要的是某種“演算法”,你可以在其中輸入表格的“得分元組”(math_score,stats_score)。它會告訴你某個學生是圖形上的紅點還是綠點(紅色/綠色也可稱為類或標籤)。當然,該演算法以某種方式體現了我們已經擁有的資料中存在的模式,也稱為訓練資料。
在這種情況下,找到穿過紅點即和綠點集之間的直線,然後確定得分元組落在該線的哪一側,是一個很好的演算法。我們採取一方——綠色方面或紅色方面——作為她在課程中最有可能表現的一個指標。
這裡的直線就是我們的分割邊界(separating boundary)(因為它分隔了標籤)或分類器(我們用它來對點進行分類)。該圖展示了在我們的問題中兩種都有可能的產生的分類器。
好的 vs 壞的分類器
這是一個有趣的問題:上面的兩條線都可以將紅色和綠色的資料集分開。我們是否有充分的理由選擇其中一個而不是另一個?
請記住,分類器的價值不在於它如何區分訓練資料。我們最終希望它對尚未看到的資料點進行分類(稱為測試資料)。鑑於此,我們希望選擇一條線來捕獲訓練資料中的基本模式,因此很有可能它在測試資料上表現良好。
上面的第一條直線看起來有點“傾斜”。在它的下半部分附近,它似乎太靠近紅點色資料集了,而在它的上半部分它太靠近綠色資料集了。當然,它可以完美地分離訓練資料,但是如果測試點離資料集稍遠一點,那麼它很可能會得到一個錯誤的標籤。
第二條直線沒有這個問題。例如,看看下圖中已正方形顯示的測試點以及分類器指定的標籤。
第二條直線儘可能遠離兩個資料集,同時使訓練資料正確分離。它通過兩個資料集的中間部分,它不那麼“冒險”,可以為每個類提供一些空間來佈置資料分佈,從而很好的適用於測試資料。
SVM 試圖找到這第二種線。我們通過視覺選擇了更好的分類器,但我們需要更精確地定義基礎原理以便在一般情況下應用它。這是 SVM 的簡化版本:
- 找到能夠正確分類訓練資料的直線。
- 在所有這些直線中,選擇與它最近的點距離最遠的直線。
距離這條直線的最近那些點稱為支援向量(support vectors)。他們圍繞這條線定義的區域稱為間隔(margin)。
下面顯示的是第二條直線的支援向量:帶有黑色邊緣的點(有兩個)和間隔(陰影區域)。
支援向量機為您提供了一種在許多可能的分類器之間進行選擇的方法,以確保以更高的正確率標記測試資料。這種方法很簡潔吧?
雖然上圖顯示了在二維空間中的直線和資料,但必須注意 SVM 在任意數量的維度上都可以執行;
在這些維度中,他們找到了二維直線的類比。
例如,在三維空間中,他們尋找平面(plane)(我們將很快看到這個例子),並且在更高的維度中,他們尋找超平面(hyperplane) ——二維直線和三維平面到任意數量的維度的推廣。
可由直線(或通常為超平面)分隔的資料稱為線性可分(linearly separaterable) 資料。超平面充當線性分類器(linear classifier)。
容錯
我們在最後一節中檢視了完全線性可分離資料的簡單情況。然而,真實世界的資料通常是混亂的。你幾乎總會遇到一些線性分類器無法正確分隔的例項。
以下是此類資料的示例:
顯然,如果我們使用線性分類器,我們永遠無法完全分離標籤。我們也不想完全拋棄線性分類器,因為除了一些錯誤的點之外,它看起來似乎很適合這個問題。
SVM 如何處理這個問題?它們允許您指定您願意接受的錯誤數量。
您可以為 SVM 提供一個名為“C”的引數;這允許你決定以下兩者之間的權衡:
- 有很大的間隔。
- 正確分類訓練資料。較高的 C 值意味著您希望訓練資料上的錯誤較少。
值得重申的是,這是一個 權衡(tradeoff) 辦法。您可以在 代價(expense) 範圍內為訓練資料選擇更好地分類器。
下面的圖顯示了當我們增加 C 的值時,分類器和間隔是如何變化的(支援向量未顯示):
注意當我們增加 C 的值時,直線如何“傾斜”。在高值時,它會嘗試容納圖表右下方存在的大多數紅點。這可能不是我們想要的測試資料。C=0.01 的第一個圖似乎更好地捕捉了總體趨勢,儘管與 較高 C 值的結果相比,訓練資料的準確度較低。
由於這是一個權衡辦法,請注意當我們增加 C 的值時,間隔的寬度會縮小。
在前面的例子中,間隔是資料點的“無人之地”。在這裡,我們看到不可能有這樣一種狀況,既有一個良好的分割邊界,又在間隔中不存在任何點。實際上一些點進入到了間隔裡面。
一個重要的實際問題是為 C 確定一個好的值。由於現實世界的資料幾乎從不可分離,因此這種需求經常出現。我們通常使用像 交叉驗證(cross-validation) 這樣的技術為 C 選擇一個好的值。
非線性可分離資料
我們已經看到支援向量機如何系統地處理完美/幾乎線性可分離的資料。它如何處理絕對不可線性分離的資料的情況呢?畢竟,很多現實世界的資料屬於這一類。當然,尋找超平面已不再適用。鑑於 SVM 在這項任務上表現出色,這似乎很不幸。
以下是非線性可分資料的示例(這是著名的 XOR 資料集的變體),與線性分類器 SVM 一起顯示:
你一定會認為這看起來不太好。我們在訓練集上的準確率只有 75% ——這是隻用一條直線進行分隔所能達到的最優效能。更重要的是,這條直線非常靠近一些資料。最優的準確度也並不是很好,而且為了達到平衡,這條線幾乎完全跨過了一些點。
我們需要做得更好
這就是我對 SVM 最喜歡的一點。這是我們到目前為止所擁有的:我們有一種非常擅長尋找超平面的技術。但是,我們也有不可線性分離的資料。那麼我們該怎麼辦?將資料投影到一個可以線性分離的空間,並在這個空間中找到一個超平面!
我將一步一步地講解這個想法。
我們從上圖中的資料集開始,並將其投影到三維空間中,其中新座標為:
這就是投影資料的樣子。你看到我們可以在平面上滑動的平面嗎?
讓我們執行 SVM 吧:
好啦!我們完美地將標籤分離!讓我們將平面投射回原始的二維空間,看看分割邊界是什麼樣的:
在訓練資料集上有 100% 的精度並且分隔邊界不會太靠近資料!好極了!
原始空間中分割邊界的形狀取決於投影。在投影空間中,這往往是一個超平面。
請記住,投影資料的主要目的是為了利用 SVM 發現分隔超平面的能力。
將其對映回原始空間時,分割邊界不再是直線。對於間隔和支援向量也是如此。就我們的視覺直覺而言,它們在投射空間中是有意義的。
看看它們在投影空間中的樣子,然後是原始空間。3D 間隔是分離超平面上方和下方的平面之間的區域(沒有陰影以避免視覺混亂)。
在投影空間中有 4 個支援向量,這似乎是合理的。它們位於定義間隔的兩個平面上。在原始空間中,它們仍然處在間隔上,但到這一步似乎還不夠。
讓我們退一步分析發生的事情:
1.我怎麼知道將資料投射到哪個空間?
看起來我完全明確該怎麼做——在那裡放置一個 2 的平方根!
在這個例子中,我想展示的是向高維的投影是如何工作的,所以我選擇了一個非常具體的投影。一般來說,這一點是很難知道的。然而,我們所知道的是,由於 Cover 定理,當投影到更高維度時,資料更可能是線性可分的。
在實踐中,我們嘗試一些高維投影,看看哪些有效。實際上,我們可以將資料投影到無限維度,並且通常效果還不錯。這值得詳細討論,也就是下一節的內容。
2. 我應該首先投影資料,然後執行 SVM 嗎?
不。為了使上面的例子易於掌握,我的做法看起來好像我們需要首先投影資料。事實上,你要求 SVM 為你進行投影。這有一些好處。首先,SVM 使用一些名為**核函式(kernel)**的東西進行這些投影,這些投影非常快(我們很快就會看到)。
另外,還記得我在前一節提到的投射到無限維度嗎?如果你自己投影資料,你如何表示或儲存無限維度?事實證明,SVM 對此非常聰明,同樣得益於核函式。
現在是時候來看看核函式了。
核函式
最後,讓SVM 有效工作是有祕訣的。這也是我們需要學習數學知識的地方。
讓我們來看看到目前為止我們所看到的情況:
- 對於線性可分的資料,SVM 表現得非常好。
- 對於幾乎可線性分離的資料,通過使用正確的 C 值,SVM 仍然可以很好地執行。
- 對於不能線性分離的資料,我們可以將資料投影到完全/幾乎可線性分離的空間,從而將問題降至第 1 步或第 2 步,我們又重新開始處理資料。
看起來,將 SVM 普遍適用於各種情況的一件重要操作是是將它投射到更高的維度。這就是核函式的用處。
首先,說點題外話。
SVM 的一個非常令人驚訝的地方是,在它使用的所有數學運算中,精確投影,甚至維數的數量都沒有顯現。你可以根據各種資料點(表示為向量)之間的點積(dot products) 來表達所有內容。對於 p 維向量的 i 和 j,其中第一個下標表示某一個點,第二個下標表示維度編號:
點積是這樣定義的:
如果我們的資料集中有 n 個點,則 SVM 僅僅需要通過每對點的點積來構建分類器。僅此而已。當我們想要將資料投影到更高維度時,也是如此。我們不需要為 SVM 提供精確的投影;我們需要在投影空間中的所有點的組合之間計算點積。
這是有重大意義的,因為這正是核函式所做的。核函式(kernel function的縮寫)在原始空間中將兩個點作為輸入,並直接在投影空間中給出點積。
讓我們重新審視之前做過的投影,看看我們是否可以提出相應的核函式。我們還將留意為投影執行的計算次數,然後計算點積——看看如何使用核函式進行比較。
對於點 i:
我們相應的投影點是:
要計算此投影,我們需要執行以下操作:
- 獲得新的第一維資料:1 次乘積
- 第二維資料:1 次乘積
- 第三維資料:2 次乘積
總共,1+1+2 = 4 次乘積。
新維度中的點積是:
要計算兩個點 i 和 j 的點積,我們需要先計算它們的投影。因此,4 + 4 = 8 次乘積,然後點積本身需要 3 次乘法和 2 次加法。
總之,就是:
- 乘積:8(投影)+ 3(點積)= 11 次乘積
- 加法:2(點積)
總共是 11 + 2 = 13 次運算。
我宣告這個核函式的結果是一樣的:
我們首先在原始空間中取向量的點積,然後對結果進行平方運算。
讓我們展開它並檢查我的說法是否正確:
確實如此。這需要多少次運算?看看上面的第(2)步。要計算二維的點積,我需要 2 次乘法和 1 次加法。平方是另一種乘法。
所以,總共是:
- 乘法:2(原始空間中的點積)+ 1(對於平方結果)= 3 次乘法
- 加法:1(原始空間中的點積)
共計 3 + 1 = 4 次運算。這只是我們之前需要的進行的 31% 的運算量。
看起來使用核函式來計算我們需要的點積更快。這可能看起來不是什麼大問題:我們正在對比 4 次運算和 13 次運算,但是隨著輸入點的維度越來越多,並且投影空間的維度越來越高,大型資料集的計算節省的時間就越來越多。這就是使用核函式的一個巨大優勢。
大多數 SVM 庫已經預先打包了一些流行的核函式,如 多項式、徑向基函式(RBF)和Sigmoid函式。當我們不使用投影時(如本文的第一個例子),我們在原始空間中計算點積——我們把這個稱之為線性核函式。
其中許多核函式為您提供了額外的手段,可以根據您的資料進一步調整它。例如,多項式核函式:
允許您選擇 c 和 d 的值(多項式的次數)。對於上面的 3D 投影,我使用了 c = 0 和 d = 2 的多項式核函式。
但是我們還沒有完成核函式的強大功能!
還記得我之前提到過的投射到無限維度嗎?如果您還沒有猜到,其實讓它工作的方法就是擁有合適的核函式。這樣,我們就不必對輸入資料進行投影,也不用擔心儲存無限維資料的問題。
如果你有準確的投影資料,核函式將會計算點積。
RBF 核函式通常用於特定的無限維投影。我們將不在這裡進行數學計算,請檢視本文末尾的參考資料。
我們怎樣才能在無限維度的情況下仍然可以計算點積?如果您發現這個問題令人困惑,請考慮我們如何計算無窮級數的和。類似的,點積中有無限項,但恰好存在計算其總和的公式。
這回答了我們在上一節中提出的問題。總結一下:
- 我們通常不會為我們的資料定義具體的投影。相反,我們從可用核函式中挑選,在某些情況下調整它們,以找到最適合資料的核函式。
- 當然,沒有什麼能阻止我們定義自己的核函式,或者自己執行投影,但在很多情況下我們並不需要這麼做。或者我們至少從我們能做的事情開始。
- 如果有可用於我們想要的投影的核函式,我們一般選擇使用核函式,因為它通常計算更快
- RBF 核函式可以將點投影到無限維度。
開始使用 SVM 庫
有很多 SVM 庫供你開始練習:
像 scikit-learn 這樣的許多通用 ML 庫也提供 SVM 模組,這些模組通常是專用 SVM 庫的包裝器。我的建議是從經過試驗測試的 libSVM 開始。
libSVM 可用作命令列工具,但下載檔案也捆綁了 Python、Java 和 Matlab 包裝器。只要你有一個包含 libSVM 能夠理解的格式的資料檔案(下載的 README 檔案解釋了這個,以及其他可用的選項)你就能夠使用它。
事實上,如果你需要非常快速地瞭解不同的核函式和不同的 C 值等等是如何影響尋找分割邊界的,請在其主頁上嘗試使用“圖形介面”。標記屬於不同類的資料點,選擇 SVM 引數,然後點選 Run!
我迫不及待地迅速標出幾個點:
是的,我不是讓 SVM 變得容易。
然後我嘗試了幾個核函式:
介面不顯示分割邊界,但顯示 SVM 學習屬於特定標籤的區域。如你所見,線性核函式完全忽略了紅點。它認為整個空間為黃色(一說綠色)。但是 RBF 核函式巧妙地使用了戒指形狀的區域覆蓋了紅色標記!
有用的資源
我們一直主要依靠視覺上的直觀理解。雖然這是獲得初步理解的好方法,但我強烈建議您深入挖掘。視覺上的直觀理解的例子可能不足以理解間隔寬度以及用於非線性可分離情況的支援向量。
請記住,這些數量是通過優化權衡來決定的。除非你去看數學原理,否則一些結果可能看似違反直覺。
數學有用的另一個方面是理解核函式。我在這篇短文中幾乎沒有介紹過 RBF 核函式。我希望它的“神祕”感——它與無限維投影的關係再加上最後一個資料集(“環”)上的奇妙結果——已經說服你去仔細研究它。
我推薦的資源:
- 視訊講座:從資料中學習。作者是 Yaser Abu-Mostafa。講座從 14 到 16 部分討論了 SVM 和核函式。如果你正在尋找 ML 的簡介,我也強烈推薦整個系列,它在數學和直覺之間保持著良好的平衡。
- 書:統計學習的要素。作者是 Trevor Hastie、Robert Tibshirani 和 Jerome Friedman。第 4 章介紹了 SVM 背後的基本思想,第 12 章則全面論述了它。
好好學習,天天向上!
如果發現譯文存在錯誤或其他需要改進的地方,歡迎到 掘金翻譯計劃 對譯文進行修改並 PR,也可獲得相應獎勵積分。文章開頭的 本文永久連結 即為本文在 GitHub 上的 MarkDown 連結。
掘金翻譯計劃 是一個翻譯優質網際網路技術文章的社群,文章來源為 掘金 上的英文分享文章。內容覆蓋 Android、iOS、前端、後端、區塊鏈、產品、設計、人工智慧等領域,想要檢視更多優質譯文請持續關注 掘金翻譯計劃、官方微博、知乎專欄。