1.理解支持向量機(SVM)
1)SVM特點
- 支持向量機和神經網絡都是“黑箱模型”的代表:潛在的模型基於復雜的數學系統,而且結果難以解釋。
- SVM的目標是創建一個平面邊界(“超平面”),使得任何一邊的數據划分都是均勻的。結合了kNN和線性回歸。
- 幾乎適用於所有的學習任務,包括分類和數值預測。
2)用超平面分類
- 線性可分:可以由一條直線或一個平面進行划分

- 最大間隔超平面(MMH):很多線都能對數據點進行分類,但要尋找能使類形成最大間隔的那條線(因為在邊界附近點位置的微小變化可能導致某些點落在線之外),支持向量就是每個類中最接近最大間隔超平面的點。所以單獨使用支持向量,就能定義最大間隔超平面。

- 線性可分條件下,最大間隔超平面要盡可能遠離兩組數據點的外邊界(“凸包”),最大間隔超平面就是兩個凸包之間的最短距離直線的垂直平分線,可通過“二次優化”算法實現。

- 非線性可分:數據不是線性可分的條件下,使用一個“松弛變量”來創建一個軟間隔,允許一些點落在線不正確的一邊。

- 非線性可分中的成本參數C:即所有違反約束的點,試圖使總成本最小,而非尋找最大間隔。修改C將調整對於落在超平面錯誤一邊的案例的懲罰。C越大,實現100%分離的優化就越困難。較小的C將把重點放在更寬的整體邊緣。
3)對非線性空間使用核函數
- 另一種處理非線性問題的方法,就是使用“核技巧”的處理將問題映射到一個更高維的空間,這樣非線性關系可能會變為完全線性。

- 從本質上講,核技巧涉及一個添加能夠表述度量特征之間數學關系新特征的過程。
- 非線性核SVM的特點:

- 核函數:線性核函數(特征的點積),多項式核函數(加一個非線性數據變換),S形核函數(類似神經網絡的S形激活函數),高斯RBF核函數(類似RBF神經網絡)。多數情況下,核函數的選擇是任意的,因為性能可能只有輕微的變化。
2. 支持向量機應用示例
使用SVM進行光學字符識別(OCR圖像處理):通過將印刷或手寫文本轉換為電子形式,保存在數據庫種來處理紙質文件。
難點:
- 圖像的規則模式很難嚴格定義
- 圖像數據往往是噪聲數據
1)收集數據
數據集包含26個大寫英文字母的2000個案例,使用20種不同的隨機重塑和扭曲的黑斯和白色字體印刷。
假設當圖像字符被掃描到計算機,轉換為像素,有16個統計屬性(如水平垂直尺寸,黑色像素比例等)。

數據下載:
鏈接: https://pan.baidu.com/s/1q8zHWkMZcapwnX90PA4hOg 提取碼: eaqt
2)探索和准備數據
SVM需要所有特征都是數值型的,而且每一個特征需要縮小到一個相當小的區間內。所以不要有因子,而且要做標准化。這里略過沒做。
## Example: Optical Character Recognition ----
## Step 2: Exploring and preparing the data ----
# read in data and examine structure
letters <- read.csv("letterdata.csv")
str(letters)
# divide into training and test data
letters_train <- letters[1:16000, ] #80%
letters_test <- letters[16001:20000, ] #20%
3)訓練數據
SVM的R包有e1071,klaR和kernlab等,這里用kernlab(與caret連用,允許SVM使用各種自動化方法進行訓練和評估)。
kernlab::ksvm(target~predictors,
data=mydata,
kernel="rbfdot", #隱非線性映射,rbfdot/polydot/tanhdot/vanilladot
c=1) #違法約束條件的懲罰,較大的c值導致較窄的邊界
訓練:
## Step 3: Training a model on the data ----
# begin by training a simple linear SVM
library(kernlab)
letter_classifier <- ksvm(letter ~ ., data = letters_train,
kernel = "vanilladot") #默認使用高斯RBF核函數,這里用線性函數
# look at basic information about the model
letter_classifier

4)評估模型
letter_predictions <- predict(letter_classifier, letters_test)
head(letter_predictions)
table(letter_predictions, letters_test$letter)

# look only at agreement vs. non-agreement
# construct a vector of TRUE/FALSE indicating correct/incorrect predictions
agreement <- letter_predictions == letters_test$letter
table(agreement)
prop.table(table(agreement))

識別的准確度大概為84%。
5)提高性能
可以使用一個更復雜的核函數,將數據映射到更高維的空間,獲得一個較好的模型擬合度。如試試高斯RF核函數,或者修改成本約束參數C值來修正決策邊界的寬度。
## Step 5: Improving model performance ----
set.seed(12345)
letter_classifier_rbf <- ksvm(letter ~ ., data = letters_train, kernel = "rbfdot") #高斯RBF核函數
letter_predictions_rbf <- predict(letter_classifier_rbf, letters_test)
agreement_rbf <- letter_predictions_rbf == letters_test$letter
table(agreement_rbf)
prop.table(table(agreement_rbf))

訓練時間更長,將准確度提高到了93%。
機器學習與R語言系列推文匯總:
【機器學習與R語言】1-機器學習簡介
【機器學習與R語言】2-K近鄰(kNN)
【機器學習與R語言】3-朴素貝葉斯(NB)
【機器學習與R語言】4-決策樹
【機器學習與R語言】5-規則學習
【機器學習與R語言】6-線性回歸
【機器學習與R語言】7-回歸樹和模型樹
【機器學習與R語言】8-神經網絡
【機器學習與R語言】9-支持向量機
【機器學習與R語言】10-關聯規則
【機器學習與R語言】11-Kmeans聚類
【機器學習與R語言】12-如何評估模型的性能?
【機器學習與R語言】13-如何提高模型的性能?
