目录
一、引言
1.背景
分类问题是机器学习中一个核心的问题,它涉及到识别给定数据集中的项目(或数据点)属于预定的一组类别中的哪一个。在分类问题中,目标是构建一个模型(或分类器),该模型能够准确地将新的、未见过的数据分配到这些类别中的一个。
2.应用
支持向量机(SVM)是一种强大的监督学习方法,用于分类、回归甚至异常检测。由于其独特的优化原理和核技巧的灵活应用,SVM在多个领域都有广泛的应用。
生物信息学:在生物信息学中,SVM被用于分类蛋白质、疾病预测以及基因表达数据的分析。例如,它可以帮助识别与特定疾病相关的基因变体。
图像识别:SVM在图像处理和计算机视觉领域,尤其是在图像分类和识别任务中非常有效。例如,它可以用于面部识别、手写数字识别和车牌识别。
文本和超文本分类:SVM可以用于文本文件的自动分类,这对于垃圾邮件过滤、新闻文章分类和网页分类等任务非常有用。
二、基本概念
SVM的主要目的是在数据集中找到一个最优的分割平面(在二维空间中是一条线,在三维空间中是一个平面,更高维度中称为超平面),这个平面能够最好地分隔不同类别的数据。
1.SVM 的基本思想
SVM寻找一个超平面,使得它能够将不同类别的数据分开,并确保两边数据到这个平面的距离最大化。(其中这个这个距离被称为“间隔”,SVM通过最大化这个间隔来提高模型的泛化能力。)
2.支持向量的概念
支持向量是指那些离分割超平面最近的数据点。实际上,这些点直接支撑着或定义了这个超平面的位置和方向。换句话说,支持向量是决定分割边界的关键数据点。这意味着,只有这些支持向量的位置改变了,最终的超平面的位置才会改变。其他非支持向量的数据点可以移动或者删除而不会影响超平面的定位,只要它们不穿过这个边界。
图:
3.间隔的概念
间隔定义为数据点到超平面的最短距离。间隔分为两部分:正间隔和负间隔。最大化间隔实际上是找到一个平衡点,使得最近的两边数据点到超平面的距离尽可能大。(SVM 的目标就是最大化这个间隔,以此提高模型或分类器的泛化能力)
图:
三、SVM的数学原理
1.对于线性可分的数据集,线性SVM的目标是找到一个超平面,即,其中
w
是超平面的法向量,x
是数据点,b
是偏差项。
图:在二维平面,超平面为直线
然后根据w的正负即可判断数据点x的类别。
引入标签:每个数据点 都有一个类别标签
,其中
的值为 +1 或 -1。对于所有
,应满足:
这个不等式(即
)确保所有数据点都正确分类,并且距离超平面至少为 1。
最大化间隔:间隔被定义为数据点到决策边界的最短距离的两倍。为了最大化间隔,需要最小化 (或其平方
)。因此,优化问题可写为:
这里,因子 1/2 是为了后续计算方便而添加的,并不影响最优解。
最大化间隔约束:间隔优化问题需满足约束: 这个约束保证了所有数据点至少距离决策超平面为 1,从而在超平面两侧形成一个“边界”。
由于现在有两个函数,引入拉格朗日乘数法
为了解这个带约束的优化问题,我们引入拉格朗日乘数 。拉格朗日函数为:
其中,是对应于每个数据点的拉格朗日乘数。
通过将拉格朗日函数 ( L ) 对 ( w ) 和 ( b ) 的偏导数设为 0,我们可以得到:
将这些条件代回拉格朗日函数,得到对偶形式:
2.对于线性不可分的数据集,引入核函数
对与线性不可分的的数据集在低纬度上可能是不可分的,而将它们投影到高维度时,就成了可以分开的,但高纬度的数据往往计算量巨大,耗费时间长,这时我们就可以引用核函数
核函数的作用:用低纬度的函数表示高维度的值
但核函数只有特定的几个,例如 或
四、SVM的应用实例
1.代码展示
import numpy as np
# 假设一个简单的二维线性可分数据集
X = np.array([[1, 2], [2, 3], [3, 3], [6, 5], [7, 8], [9, 8]]) # 特征集
y = np.array([-1, -1, -1, 1, 1, 1]) # 类别标签
# 初始化权重w和偏置b
w = np.zeros(len(X[0]))
b = 0
# 学习率和迭代次数
learning_rate = 0.001
epochs = 10000
# 训练SVM
for epoch in range(1, epochs):
for i, x in enumerate(X):
# 检查是否满足y(w*x+b)≥1条件
if (y[i] * (np.dot(x, w) + b)) < 1:
# 错误分类,更新权重和偏置
w += learning_rate * ((y[i] * x) + (-2 * (1/epoch) * w))
b += learning_rate * y[i]
else:
# 正确分类,仅更新权重
w += learning_rate * (-2 * (1/epoch) * w)
# 显示训练后的权重和偏置
print("权重:", w)
print("偏置:", b)
# 使用训练后的权重和偏置对同一个数据集进行分类
for i, x in enumerate(X):
# 计算决策函数的值
decision = np.dot(x, w) + b
# 分类
pred = 1 if decision > 0 else -1
print(f"样本 {x} 的预测标签是: {pred}")
import matplotlib.pyplot as plt
# 绘制数据点
for d, sample in enumerate(X):
if y[d] < 0:
plt.scatter(sample[0], sample[1], s=120, marker='_', linewidths=2)
else:
plt.scatter(sample[0], sample[1], s=120, marker='+', linewidths=2)
# 添加数据点的代码之后,我们计算并绘制决策边界
# 计算决策边界的斜率和截距
slope = -w[0] / w[1]
intercept = -b / w[1]
# 设定x轴的范围以便绘制直线
ax = plt.gca()
xlim = ax.get_xlim()
ylim = ax.get_ylim()
# 生成x值的连续序列
x = np.linspace(xlim[0], xlim[1], 30)
# 计算对应的y值
y_plot = slope * x + intercept
plt.plot(x, y_plot, 'k-')
# 重新设置x和y的限制
ax.set_xlim(xlim)
ax.set_ylim(ylim)
# 添加图的标签和标题
plt.xlabel('Feature 1')
plt.ylabel('Feature 2')
plt.title('SVM Decision Boundary')
plt.show()
请注意,这个实现非常原始,它没有包括很多SVM的关键特性,比如:
- 核函数,让SVM可以处理非线性问题。
- 支持向量,只有离决策边界最近的点应该影响模型的形成。
- 有效的停止条件和对超参数的优化,如C参数的选择。
- 实际应用中的数据通常需要进行归一化和预处理。
2.结果展示
五、SVM的优缺点
1.优点
有效处理高维空间:SVM特别适合于特征比样本数量多的情况,即高维空间。这是因为SVM通过寻找最优超平面来分类数据,不直接依赖于数据的维度。
在中小型数据集上表现良好:SVM在处理中小型数据集时通常表现出色,尤其是在数据集线性可分或接近线性可分的情况下。
泛化能力强:通过最大化间隔,SVM旨在提高模型的泛化能力,减少过拟合的风险。
使用核技巧处理非线性数据:SVM可以通过核技巧(如多项式核、径向基函数核等)将数据映射到高维空间,从而有效地处理非线性分类问题。
支持向量的特性:模型的复杂度取决于支持向量的数量,而不是整个数据集的大小,这有助于减少模型参数的数量。
2.缺点
对大规模数据集效率较低:SVM在处理大规模数据集时可能会变得非常慢,因为需要计算和存储核矩阵,这会导致计算和存储资源的需求增加。
参数调整敏感:SVM的性能高度依赖于正确的参数选择,包括选择合适的核函数和调整正则化参数C。这需要专业知识和经验,或者大量的实验。
解释性较差:与决策树等模型相比,SVM的决策过程较难解释和理解,这使得它在需要模型透明度的应用中不太适用。
多分类问题处理复杂:虽然SVM可以用于多分类问题,但通常需要通过组合多个二分类SVM来实现,这可能会增加模型的复杂性和计算成本。
对缺失数据敏感:SVM对数据中的缺失值比较敏感,需要预先处理缺失数据,这可能会增加数据预处理的复杂性。
六、结论
支持向量机(SVM)自从1990年代中期被提出以来,已经成为机器学习领域里最重要的方法之一。SVM基于统计学习理论的结构风险最小化原则,旨在最小化泛化误差,这使得它从理论上就保证了良好的学习效果。这种坚实的理论基础让SVM在众多实际应用中显示出稳定性和可靠性。SVM能够有效处理高维数据和解决复杂的非线性问题,尤其是通过引入核技巧后,能够处理那些非线性可分的数据。