标签:好处 1.2 elf 联想 this sig add unicode 修改
在上一篇中,讲述了感知机是什么。接下来将叙述感知机的对偶形式,这在解决支持向量机问题中非常有用,因为直接求解存在困难时,我们往往会把它变换到其等价形式进行求解。这篇将继续上篇内容,把遗留的两个问题解释清楚。
现在考虑感知机学习算法的对偶形式。感知机学习算法的原始形式和对偶形式在支持向量机学习算法的原始形式和对偶形式相对应。
对偶形式的基本想法是,将
逐步修改
这里,
算法(感知学习算法的对偶形式)
输入:线性可分的数据集
T={(x1,y1),(x2,y2),...,(xN,yN)}, 其中xi∈Rn,yi∈{?1,+1}; 学习率η(0<η<1);
输出:α,b; 感知机模型f(x)=sign(∑Nj=1αjyjxj?x+b). 其中α=(α1,α2,...,αN)T.
(1)α←0,b←0
(2) 在训练集中选取数据(x_i,y_i)
(3) 如果yi(∑Nj=1αjyjxj?xi+b)≤0
αi←αi+η b←b+ηyi
(4) 转至(2)直到没有误分类数据。
对偶形式中训练实例仅以内积的形式出现。为了方便,可以预先将训练集中实例间的内积计算出来并以矩阵的形式存储,这个矩阵就是所谓的Gram矩阵
总觉得,了解到这缺了点什么。我们无法直观的看出任何含义,改变
参看算法步骤3.
但不管如何,我们能看出步骤3.式是为了寻找各
本训练集采用与前文相同的数据集。
训练集:training.data
第一列和第二列分别是特征向量
3.542485 1.977398 -1
3.018896 2.556416 -1
7.551510 -1.580030 1
2.114999 -0.004466 -1
8.127113 1.274372 1
7.108772 -0.986906 1
8.610639 2.046708 1
2.326297 0.265213 -1
3.634009 1.730537 -1
0.341367 -0.894998 -1
对偶形式的初始化代码与基本感知机算法相一致。只是比之多了createGram()方法:
if __name__ == "__main__":
if len(sys.argv) !=4:
print "Usage: python duality.py eta trainFile modelFile"
exit(0)
eta =float(sys.argv[1])
trainFile = file(sys.argv[2])
modelFile = file(sys.argv[3],‘w‘)
lens =0
for line in trainFile:
chunk =line.strip().split(‘ ‘)
lens = len(chunk) -1
temp_all =[]
tmp =[]
for i in range(1,lens+1):
tmp.append(float(chunk[i]))
temp_all.append(tmp)
temp_all.append(int(chunk[0]))
training_set.append(temp_all) #初始化training_set
trainFile.close()
#生成Gram矩阵,和我们自己定义的G‘‘矩阵半斤八两
createGram()
for i in range(len(training_set)):
a.append(0)#初始化alpha
for i in range(lens):
w.append(0)#初始化w
for i in range(1000):
check()#这里的作用便是检查我们的G‘‘矩阵的每一列是否符合条件
print "The training_set is not linear separable. "
计算某两个向量内积:
def calInnerProduct(i,j):
global lens
res =0
for p in range(lens):
res += training_set[i][0][p] * training_set[j][0][p]
#p是每个向量的纬度,从1到N变换,当然代码里从0开始到N-1
#i和j分别表示在M个输入集中,第i个向量和第j个向量
return res
向量相加与系数相乘:
def AddVector(vec1,vec2):
for i in range(len(vec1)):
vec1[i] =vec1[i]+vec2[i]
return vec1
def NumProduct(num,vec):
for i in range(len(vec)):
vec[i] *=num
return vec
生成Gram矩阵:
def createGram():
#思路非常清晰,len求出训练集的M大小
#外层遍历行,内层遍历列,求出的结果append到Gram中去
global lens
for i in range(len(training_set)):
tmp = []
for j in range(0,len(training_set)):
tmp.append(calInnerProduct(i,j))
Gram.append(tmp)
更新
def update(k):
#注意此处的更新,更新的是alpha和b,在G‘‘矩阵中更新的是第k行的alpha
global a,b,eta
a[k] +=eta
b = b+eta*training_set[k][1]
步骤3式
def cal(k):
#结合G‘‘矩阵,这段代码就非常容易阅读,但此处的K与上述更新的k并不表示一个含义,在G‘‘中,表示对第k列做相关操作
global a,b
res =0
for i in range(len(training_set)):
#针对第k列,对该列进行累加
res += a[i]*int(training_set[i][1])*Gram[i][k]
res +=b
res *=training_set[k][1]
return res
判别式
def check():
global w,a
flag = False
for i in range(len(training_set)):
#对G‘‘矩阵中的每一列做判断,这里值得注意的是,某一列不符合条件,就更新对应该行的alpha和b,即i=j所在的alpha和b
if cal(i) <= 0:
flag = True
update(i)
#直到所有列满足判别式后,flag为False不做更新,只要在符合迭代次数求出结果即可。
if not flag:
for i in range(len(training_set)):
w = AddVector(w,NumProduct(a[i]*int(training_set[i][1]),training_set[i][0]))
print "RESULT: w:",w,"b:",b
tmp =‘‘
for keys in w:
tmp+=str(keys)+‘ ‘
tmp = tmp.strip()
modelFile.write(tmp+‘\n‘)
modelFile.write(str(b)+‘\n‘)
modelFile.write(str(lens)+‘\n‘)
modelFile.write(str(eta)+‘\n‘)
modelFile.close()
os._exit(0)
flag = False
根据实际的算法,我们再来看看我们定义的
上述内容是我所学感知机的全部内容,目前所能理解的也就是这个层次。有任何疑问或者对我的推导有质疑的,欢迎留言,一起探讨。
感知机只是针对监督学习,二元分类的小怪,真正的大怪要登场了,它是什么样子的呢?我们立马走进来看看。
书本《统计学习方法》定义为:支持向量机(support vector machine,SVM)是一种二类分类模型。它的基本模型是定义在特征空间上的间隔最大的线性分类器,间隔最大使它有别于感知机(第一个特征来了!间隔最大化);支持向量机还包括核技巧,这使它成为实质上的非线性分类器。(第二个特征,解决线性不可分问题)。支持向量机的学习策略就是间隔最大化,可形式化为一个求解凸二次规划的问题,也等价于正则化的合页损失函数的最小化问题。支持向量机的学习算法是求解凸二次规划的最优算法。
1.间隔最大化,是什么东西?好抽象,看图秒懂。
2.核技巧?解决线性不可分问题?公式推导来,咱们立马给你推。
3.凸二次规划的问题,合页的损失函数最小问题。。。推荐《算法导论》中关于线性规划的章节,还不够,那就请看Convex Optimization Overview.
凸二次规划,可以这样理解,一个函数可以存在极值,但存在极值的函数在某一个局部的极值不一定是函数的极值,为什么要叫定义一个凸函数呢,因为凸函数的极值是唯一的,从局部求解出的极值问题就能代表该凸函数的极值。
支持向量机学习方法包含构建由简至繁的模型:线性可分支持向量机(linear support vector machine in linearly separable case)、线性支持向量机(linear support vector machine)及非线性支持向量机(non-linear support vector machine)。简单模型是复杂模型的基础,也是复杂模型的特殊情况。当训练数据线性可分时,通过硬间隔最大化(hard margin maximization),学习一个线性的分类器,即线性可分支持向量机,又称为硬间隔支持向量机;当训练数据近似线性可分时,通过软间隔最大化(soft margin maximization),也学习一个线性的分类器,即线性支持向量机,又称为软间隔支持向量机;当训练数据线性不可分时,通过使用核技巧 (kernel trick)及软间隔最大化,学习非线性支持向量机。
本文呈现思路历程如下:叙述线性可分支持向量机,理解间隔最大化几何含义。线性支持向量机,区分硬间隔与软间隔。非线性支持向量,理解核函数推导由来。支持向量机对偶问题,理解对偶形式的求解。序列最小最优化SMO算法,带你进入凸二次规划算法中。
直接上图,感知机解决线性可分时,我们用的图为:
支持向量机解决线性可分问题时,我们用的图为:
两幅图对比中能够直观的看出支持向量机与感知机最大的区别,感知机只需要找到一条直线把两类数据进行分割即可,但支持向量机光找到这条直线还不够,它还需要在众多直线中找寻一条符合间隔最大化的直线,作为分割线。
看图易理解,但如果没有形式化的东西,往往很难针对支持向量机设计出有效的算法来对问题进行求解,我们必须借助数学工具来对这样的问题进行建模,回归书本,咱们来看看支持向量机对该直线是如何定义的。
假设给定一个特征空间上的训练数据集
一般地,当训练数据集线性可分时,存在无穷个分离超平面可将两类数据正确分开。感知机利用误分类最小的策略,求得分离超平面,不过这时的解有无穷多个。线性可分支持向量机利用间隔最大化求最优分离超平面,这时,解释唯一的。
数学定义:给定线性可分训练数据集,通过间隔最大化或等价地求解相应的凸二次规划问题学习得到的分离超平面为
继续看图:
如图所示的二维特征空间中的分类问题。图中小圆圈表示正例,小叉叉表示负例。训练数据集线性可分,这时有许多直线能将两类数据正确划分。线性可分支持向量对应着将两类数据正确划分并且间隔最大的直线。
在上图中,有A、B、 C三个点,表示3个实例,均在分离超平面的正类一侧,预测它们的类。点A距分离超平面较远,若预测该点为正类,就比较确信预测是正确的;点C距分离超平面较近,若预测该点为正类就不那么确信;点B介于点A与C之间,预测其为正类的确信度也在A与C之间。
一般来说,一个点距离分离超平面的远近可以表示分类预测的确信程度。在超平面
函数间隔并非实际的某个误分类点到直线的距离,但却能同等的表示点距离直线的确信度。
定义函数间隔:对于给定的训练数据集T和超平面
我一直觉得函数间隔是件神奇的事情,尝试着去理解它的存在,但把它放入坐标轴后,却始终理解不了。举个例子:当
继续看图:
上图给出了超平面
数学中,我们在形式上表征了点到超平面的间隔,且能根据符号判断是否是误分类点了,这归功于神奇的
从前面的分析中我们能够明显的发现函数间隔与几何间隔相差一个
支持向量机学习的基本想法是求解能够正确划分训练数据集并且几何间隔最大的分离超平面。对线性可分的训练数据集而言,线性可分分离超平面有无穷多个(等价于感知机),但是几何间隔最大的分离超平面是唯一的。这里的间隔最大化又称为硬间隔最大化(与将要讨论的训练数据集近似线性可分时的软间隔最大化相对应)。
间隔最大化的直观解释是:对训练数据集找到几何间隔最大的超平面意味着以充分大的确信度对训练数据进行分类。也就是说,不仅将正负实例点分开,而且对最难分的实例点(离超平面最近的点)也有足够大的确信度将它们分开。这样的超平面应该对未知的新实例有很好的分类预测能力。
1.最大间隔分离超平面
下面考虑如何求得一个几何间隔最大的分离超平面(为什么不能用函数间隔来求得函数间隔最大的分离超平面?),即最大间隔分离超平面。具体地,这个问题可以表示为下面的约束最优化问题:
考虑几何间隔和函数间隔的关系式
个人觉得,单纯的几何间隔可以表示为
这样我们就可以取
上述分析完成了对支持向量机的建模,实际就是把它形式化为一个凸二次规划问题。凸优化问题是指约束最优化问题
综上所述,就有下面的线性可分支持向量机的学习算法——最大间隔法
算法(线性可分支持向量机学习算法——最大间隔法)
输入:线性可分训练数据集
其中,T={(x1,y1),(x2,y2),...,(xN,yN)} xi∈X=Rn,yi∈Y={?1,+1},i=1,2,...N
输出:最大间隔分离超平面和分类决策函数
(1) 构造并求解约束最优化问题:
minw,b12∥w∥2
s.t. yi(w?xi+b)≥1,i=1,2,...N
求得最优解w?,b?.
(2) 由此得到分离超平面:
w??x+b?=0
分类决策函数
f(x)=sign(w??x+b?)
2.支持向量和间隔边界
在线性可分情况下,训练数据集的样本点中与分离超平面距离最近的样本点的实例称为支持向量。支持向量是约束条件式等号成立的点,即
为了求解线性可分支持向量机的最优化问题,将它作为原始最优化问题,应用拉格朗日对偶性,通过求解对偶问题(dual problem)得到原始问题(primal problem)的最优解,这就是线性可分支持向量机的对偶算法(dual algorithm)。这样做的优点,一是对偶问题往往更容易求解;二是自然引入核函数,进而推广到非线性分类问题。
首先构建拉格朗日函数,为此,对每一个不等式约束引进拉格朗日乘子
(1)求
这里假设我们求出了所有的
疑问:为何能够直接推出
综上所述,对于给定的线性可分训练数据集,可以首先求对偶问题的解
算法(线性可分支持向量机学习算法)
输入:线性可分训练数据集
其中,T={(x1,y1),(x2,y2),...,(xN,yN)} xi∈X=Rn,yi∈Y={?1,+1},i=1,2,...N
输出:分离超平面和分类决策函数
(1) 构造并求解约束最优化问题:
minαi(12∑i=1N∑j=1Nαiαjyiyj(xi?xj)?∑i=1Nαi)
s.t. ∑i=1Nαiyi=0
αi≥0,i=1,2,...N
求得最优解α?=(α?1,α?2,...,α?N)T
(2) 计算:
w?=∑i=1Nα?iyixi
并选择α? 的一个正分量α?j>0, 计算
b?=yj?∑i=1Nα?iyi(xi?xj)
(3) 求得分离超平面
w??x+b?=0
分类决策函数
f(x)=sign(w??x+b?)
拉格朗日函数的引入,使得求解原始最优化问题,变成求解其对偶形式,对偶形式的具体求解可以采用SMO算法,这将在后续章节中进一步阐述。
线性可分支持向量机必须满足线性可分,但当且仅当个别数据不满足线性不可分条件时,线性可分支持向量机变得不能够适用显然条件有点苛刻。因此,我们引入了软间隔最大化,让它扩展到线性不可分的问题。
假设给定一个特征空间上的训练数据集
线性不可分意味着某些样本点
这里
有了上面的思路,可以和训练数据集线性可分时一样来考虑训练数据集线性不可分时的线性支持向量机学习问题。相应于硬间隔最大化,它称为软间隔最大化。
线性不分分的线性支持向量机的学习问题变成如下凸二次规划问题:
同理有线性支持向量机的定义。
定义(线性支持向量机)对于给定的线性不可分的训练数据集,通过求解凸二次规划问题,即软间隔最大化问题,得到的分离超平面为
同理,根据目标函数和约束条件我们构造的拉格朗日函数为:
将上述三式代入拉格朗日函数得
综合前面的结果,有下面的算法。
算法(线性支持向量机学习算法)
输入:线性可分训练数据集
其中,T={(x1,y1),(x2,y2),...,(xN,yN)} xi∈X=Rn,yi∈Y={?1,+1},i=1,2,...N
输出:分离超平面和分类决策函数
(1) 构造并求解约束最优化问题:
minαi(12∑i=1N∑j=1Nαiαjyiyj(xi?xj)?∑i=1Nαi)
s.t. ∑i=1Nαiyi=0
0≤αi≤C,i=1,2,...N
求得最优解α?=(α?1,α?2,...,α?N)T
(2) 计算:
w?=∑i=1Nα?iyixi
并选择α? 的一个正分量α?j>0, 计算
b?=yj?∑i=1Nα?iyi(xi?xj)
(3) 求得分离超平面
w??x+b?=0
分类决策函数
f(x)=sign(w??x+b?)
线性支持向量机学习算法与线性可分支持向量机学习算法的区别仅在于对
在线性不可分的情况下,将对偶问题的解
软间隔的支持向量
针对上述疑问:有了些自己的理解,简单叙述下。为什么同样的最小化目标函数,只是简单的规定了
目标函数确定完毕后,以相同的算法,我们必然能够求出符合线性可分的一些超平面解
对解线性分类问题,线性分类支持向量机是一种非常有效的方法。但是,有时分类问题是非线性的,这时可以使用非线性支持向量机。本节叙述非线性支持向量机,其主要特点是利用核技巧。为此,先要介绍核技巧。核技巧不仅应用于支持向量机,而且应用于其他统计学习问题。
1.非线性分类问题
先来抛开繁琐的定义,直接上图,非线性分类问题的本质在于,把低维不可分数据映射到高维可分,从而能够使用线性支持向量机来求解问题。而这一映射函数,便是我们所谓的核技巧。
如上图所示,针对在二维平面无法用超平面去分离两类数据,但通过某种映射表达式,我们便有了三维的数据点,而此时此刻,便可以应用线性支持向量机来求解这分离超平面了。如何从二维变成三维呢?往往我们有两种解决方案:对数据增加新的特征,尝试着是否能够根据新加入的特征,在n+1维上对数据进行分离;当寻找特征相对困难时,我们可以利用核技巧,寻找一枚映射函数,即利用原有的特征生成新的特征。从而构造出
回归数学,针对上图二维问题,设原空间为
核技巧应用到支持向量机,其基本想法就是通过一个非线性变换将输入空间(欧式空间R^n
2.核函数的定义
定义:设
个人第一次看这定义时,并没有搞明白来龙去脉,感觉书本上的定义放得太早,让人无法理解做这定义的目的是什么。暂且不分析,继续往下走走。
3.核技巧在支持向量机中的应用
我们沿用在核函数定义中的映射
在博文《支持向量机通俗导论-理解SVM三重境界》二重境界的2.2.2中,讲述了关于寻找核函数的全过程,非常简明清晰,具体的内容可以参考如下。本人秉持着学习的态度,重新按照自己的思路梳理一遍。
在对这些数据分类时,我们已知了每个点的向量
这里我们实际并没有用到核函数,因为我们还是单独的把它们进行变换后,再求向量积。那该如何找到这样的核函数呢?
寻找核函数有公的,怎么可以没有母的呢,构造核函数,需要再来一向量,为了便于区分该向量为
回忆刚才提到的映射的维度爆炸,在前一种方法已经无法计算的情况下,后一种方法却依旧能从容处理,甚至是无穷维度的情况也没有问题。
我们把这里的计算两个向量在隐式映射过后的空间中的内积的函数叫做核函数 (Kernel Function) ,例如,在刚才的例子中,我们的核函数为:
书中有关正定核的内容待续(泛函分析)
如上所述,利用核技巧,可以将线性分类的学习方法应用到非线性分类问题中去。将线性支持向量机扩展到非线性支持向量机,只需要将线性支持向量机对偶形式中的内积换为核函数。
下面叙述非线性支持向量机学习算法。
算法(非线性支持向量机学习算法)
输入:线性可分训练数据集
其中,T={(x1,y1),(x2,y2),...,(xN,yN)} xi∈X=Rn,yi∈Y={?1,+1},i=1,2,...N
输出:分离超平面和分类决策函数
(1) 选取适当的核函数K(x,z) 和适当的参数C,构造并求解最优化问题:
minαi(12∑i=1N∑j=1NαiαjyiyjK(xi,xj)?∑i=1Nαi)
s.t. ∑i=1Nαiyi=0
0≤αi≤C,i=1,2,...N
求得最优解α?=(α?1,α?2,...,α?N)T
(2) 计算:
w?=∑i=1Nα?iyixi
并选择α? 的一个正分量α?j>0, 计算
b?=yj?∑i=1Nα?iyi(xi?xj)
(3) 求得分离超平面
w??x+b?=0
分类决策函数
f(x)=sign(w??x+b?)
当
至此,关于支持向量机的原理部分已经全部阐述完毕,整体内容分为三大部分,线性可分支持向量机,能够允许容错的线性支持向量机,利用核函数实现非线性支持向量机。后续咱们将实战一把,分析libSvm源码,并用python实现最简单的序列最小最优化算法。
标签:好处 1.2 elf 联想 this sig add unicode 修改
原文地址:http://blog.csdn.net/u014688145/article/details/52943923