目录
一、简介
支持向量机(Support Vector Machine,SVM)是一种基于统计学习理论的机器学习算法,它是由Vapnik和Cortes于1995年提出的。SVM是一种二类分类模型,它的基本模型定义为特征空间上的间隔最大的线性分类器,其学习策略就是间隔最大化,同时它还能够应用于回归问题(SVR,Support Vector Regression)。
二、支持向量机(SVM)
2.1 概念
-
支持向量:在训练数据集上,那些位于决策边界附近的点被称为支持向量,因为它们是确定最优超平面的关键点。
-
超平面:在特征空间中,超平面是一个能够将数据集划分为两个不同类别的最大间隔平面。
-
间隔:间隔是指从超平面到最近的属于某一类的数据点的距离。SVM的目标是找到一个能够最大化这个间隔的超平面。
-
软间隔:由于真实世界中的数据往往存在噪声或重叠,硬间隔SVM可能无法找到合适的超平面。软间隔SVM允许一些数据点违反间隔约束,从而更好地适应复杂的数据分布。
-
核函数:当数据不是线性可分时,SVM通过使用核技巧将数据映射到高维空间,在高维空间中寻找最优超平面。常见的核函数包括线性核、多项式核、径向基函数(RBF)核和sigmoid核。
-
正则化参数C:在软间隔SVM中,参数C用于控制误分类的惩罚程度。C值越大,模型对误分类的惩罚越重,可能会导致过拟合;C值越小,模型的泛化能力更强,但可能会欠拟合。
2.2 四种分隔情况
-
线性可分(Linearly Separable): 在这种情况下,数据集可以被一个线性超平面完美地分隔。也就是说,存在一个超平面,它能够将两类数据点完全分开,没有任何一个数据点穿过超平面。线性可分问题可以通过硬间隔最大化来解决,此时的SVM模型被称为硬间隔支持向量机。
-
线性不可分(Linearly Inseparable): 当数据集由于噪声或重叠而不能被任何线性超平面完美分隔时,我们称之为线性不可分。在这种情况下,我们需要引入松弛变量(slack variables)来允许一些数据点违反间隔约束。这时的SVM模型被称为软间隔支持向量机,它通过软间隔最大化来解决分类问题。
-
非线性可分(Non-linearly Separable): 对于非线性问题,数据集在原始特征空间中无法通过任何线性超平面分隔。为了处理这种情况,SVM使用核技巧将数据映射到一个更高维的空间,在这个高维空间中数据可能是线性可分的。常用的核函数包括多项式核、径向基函数(RBF)核和sigmoid核。通过在高维空间中应用线性SVM方法,我们可以找到一个能够分隔数据的非线性超平面。
-
多分类问题(Multi-class Classification): SVM最初是为二分类问题设计的。对于多分类问题,我们需要将SVM扩展到能够处理多个类别。这可以通过一对多(one-vs-rest)策略、一对一(one-vs-one)策略或者基于决策树的层次化SVM(Hierarchical SVM)等方法来实现。在多分类问题中,我们可能需要找到多个超平面,每个超平面分隔一对类别。
2.3 相关计算
超平面方程
在SVM中,超平面是通过解优化问题得到的,其方程可以表示为:
其中,𝑤w 是超平面的法向量,决定了超平面的方向; 是截距,决定了超平面与原点的距离。对于任何点 ,如果 ,则该点被分类为正类;如果 ,则被分类为负类。
间隔
SVM中的间隔是指从超平面到最近的数据点的距离。在硬间隔SVM中,这个距离是最大的,而在软间隔SVM中,可能存在一些数据点违反间隔约束。
-
硬间隔:对于硬间隔SVM,间隔由支持向量到超平面的距离决定,可以表示为:
其中,是支持向量。硬间隔SVM的目标是最大化这个间隔,即最大化 。
-
软间隔:在软间隔SVM中,考虑到松弛变量 ,间隔的计算稍微复杂一些。优化问题变为:
这里, 是正则化参数,控制着间隔大小和误分类之间的权衡。
2.4 主要特点
- 最大间隔分类器:SVM试图找到能够最大化两类数据间隔的超平面。
- 使用核函数:通过使用核技巧,SVM能够有效地处理非线性问题。
- 硬间隔与软间隔:硬间隔SVM假设数据是线性可分的,而软间隔SVM允许一些数据点违反间隔约束。
- 支持向量:训练完成后,大部分的训练数据都不再重要,只有那些位于决策边界附近的点(支持向量)对分类有影响。
三、代码实现
3.1 主代码
import numpy as np
import matplotlib.pyplot as plt
from sklearn import svm
# 创建 40 个点
np.random.seed(0)
X = np.r_[np.random.randn(20, 2) - [2, 2], np.random.randn(20, 2) + [2, 2]]
Y = [0] * 20 + [1] * 20
Y = np.array(Y) # 将 Y 转换为 NumPy 数组以便进行索引
# 添加噪点
num_noise = 2
noise_indices = np.random.choice(range(40), num_noise, replace=False)
Y[noise_indices] = 1 - Y[noise_indices]
# 绘制原始数据点
plt.scatter(X[:, 0], X[:, 1], c=Y, cmap=plt.cm.Paired, label='Data points')
# 建立 svm 模型,并添加 C 参数来改变对噪点的敏感度
C_values = [0.1, 1, 10, 100] # 尝试不同的 C 值
colors = ['red', 'green', 'blue', 'purple']
for C, color in zip(C_values, colors):
clf = svm.SVC(kernel='linear', C=C)
clf.fit(X, Y)
# 绘制划分超平面
w = clf.coef_[0]
a = -w[0] / w[1]
xx = np.linspace(-5, 5)
yy = a * xx - (clf.intercept_[0]) / w[1]
plt.plot(xx, yy, color=color, label=f'C={C}') # 注意这里使用 color=color 而不是 color + '-'
# 圈出支持向量
plt.scatter(clf.support_vectors_[:, 0], clf.support_vectors_[:, 1],
s=80, facecolors='none', edgecolors=color, label='_nolegend_')
# 显示图例
plt.legend()
plt.axis('tight')
plt.show()
3.2 图像
四、优缺点分析
4.1 优点
- 高精度:SVM在处理小样本、非线性及高维模式识别方面表现出优势,能够捕捉到数据的复杂结构,从而获得较高的分类精度。
- 鲁棒性:SVM对数据中的噪声和异常值具有较强的抵抗力,能够保持较好的性能。
- 可扩展性:SVM能够处理大规模的数据集,并且在处理多分类问题时不需要建立复杂的映射关系。
- 易于理解:SVM的决策边界通常是直线或超平面,这使得人们对模型的解释变得容易。
- 灵活性:SVM可以通过不同的核函数来处理不同类型的数据,如线性、非线性和文本数据。
- 高效性:SVM在处理大型数据集时表现高效,可以在短时间内得到结果。
- 开源社区支持:SVM有丰富的开源库支持,如Scikit-learn、LibSVM等,便于开发者使用和定制。
4.2 缺点
- 参数选择困难:SVM的参数选择(如惩罚系数C、核函数参数gamma等)较为困难,需要通过交叉验证来确定最佳参数。
- 对稀疏数据敏感:当数据集中某些类别很少时,SVM可能无法准确预测这些类别的数据点。
- 计算复杂度高:SVM的训练过程涉及求解一个优化问题,计算复杂度较高。
- 内存消耗大:对于海量数据,SVM的训练可能会占用大量的内存资源。
- 可能过拟合:如果特征数量远大于样本数量,SVM可能会出现过拟合的情况。
五、总结
支持向量机(SVM)是一种强大的机器学习算法,广泛应用于分类和回归任务。它的核心思想是在特征空间中找到一个最优的超平面,使得不同类别的数据点能够被最佳地分隔。SVM通过最大化分类间隔来提高模型的泛化能力,并且使用核函数来处理非线性问题。
SVM在图像识别、文本分类、生物信息学、医疗诊断等多个领域有广泛的应用。它的强大泛化能力和在处理非线性问题时的有效性使其成为一个受欢迎的选择。尽管存在一些挑战,如参数选择和计算复杂度,但SVM仍然是数据科学家和机器学习工程师的重要工具。随着研究的深入和技术的进步,SVM的应用范围和能力预计将进一步扩大。