支持向量机是一个特定的优化问题,但是我不建议你自己去手动实现这一算法来求解参数θ
这里推荐两个我最常用到的库:liblinear和libsvm。
尽管你不需要自己去实现SVM,但你也需要做以下几件事:
- 选择参数CC
- 选择核函数(相似度函数)
1 核函数的选择
1.1 线性核函数(无核函数)
当你的特征数量n很大,但数据量m很小时,由于数据量不足,在这种情况下如果使用其他核函数,你可能会过拟合,因此,此时线性核函数是一个合理的选择。
1.2 高斯核函数
fi=exp(−||x−l(i)||22σ2),
我们之前讨论如何权衡偏差、方差的时候谈论过:
- 如果\sigma^2很大,那么你就有可能得到一个较高偏差较低方差的分类器。
- 如果\sigma^2很小,那么你就有可能得到一个较低偏差较高方差的分类器
使用场景:
原来的特征变量x是n维的,而且n很小,样本数量m很大时,高斯核函数会是一个不错的选择
如果你决定使用高斯核函数,那么你需要做的就是根据你所用的SVM软件包,来提供一个用于计算核函数的特定特征的方法:
注意:如果你有大小很不一样的特征变量,在使用高斯核函数之前,对它们进行归一化是很重要的。原因如下:
v=x−l
||v||2=v21+v22+…+v2n=(x1−l1)2+(x2−l2)2+…+(xn−ln)2
其中v、x、l都是向量,由于x是n维的,所以v也是n维的。
现在如果你的特征变量取值范围很不一样。例如房价预测中,
x1表示1000平方英尺,x_2表示卧室数量为2,那么
(x1−l1)可能相较于
(x2−l2)大很多。
为了让SVM更好的工作,我们需要对特征变量进行归一化处理。这将会保证SVM能够同等地关注到所有不同的特征变量。
1.3 其他核函数
不是所有你可能提出来的相似度函数都是有效的核函数。线性核函数,高斯核函数,以及其他人有时会用到的其他的核函数,他们全部需要满足一个技术条件,这个条件叫做摩赛尔定理(Mercer’s Theorem)。
大多数人最后要么使用线性核函数、要么使用高斯核函数。也有一些其他的核函数是满足摩赛尔定理的,而我个人是很少很少使用其他核函数的。
1.3.1 多项式核函数(Polynomial kernel)
将x和l之间的相似度,定义为(xTl)2:
k(x,l)=(xTl)2
这就是一个x和l相似度的估量,如果x和l每一项很接近,那么这个内积就会很大。
这是一个有些不寻常的核函数,它并不常用,但你可能会见到有人使用它的变体形式,比如:
k(x,l)=(xTl)3
k(x,l)=(xTl+1)3
k(x,l)=(xTl+5)4
这些都是多项式核函数的变形形式。
多项式核函数实际上有两个参数,一个是加在后面的常数项,如上面最后式子中的5;另一个是多项式的次数,如上面最后式子中的4。
因此,多项式核函数的更一般的形式是:
k(x,l)=(xTl+constant)degree
这种核函数并不像高斯核函数那样频繁的使用,通常他只用在当x和l都是严格的非负数时。这样以确保内积值永远不会是负数。
这捕捉到了这样一个直观感觉:如果x和l之间非常相似,也许它们之间的内积会很大。
它们也有其他的一些性质,但是人们通常用得不多。
1.3.2 其他复杂核函数(Polynomial kernel)
你也有可能会碰到其他一些更难懂的核函数,比如:
- 字符串核函数(String kernel):
如果你的输入数据是文本字符串,或者其他类型的字符串,有时会用到这个核函数。 - 卡方核函数(chi-square kernel)
- 直方图交叉核函数(histogram intersection kernel)
你可以用它们来度量不同对象之间的相似性。
例如,你在做一些文本分类问题,在这个问题中,输入变量x是一个字符串,我们想要通过字符串核函数来找到两个字符串间的相似度(但是我个人很少用这些更加难懂的核函数,我想我平生可能用过一次卡方核函数,可能用过一次或两次直方图交叉核函数,我甚至没用过字符串核函数)。
1.4 两个细节问题
1.4.1 多类分类
大部分SVM软件包已经内置了多类分类的函数了,因此,如果你用的是这种软件包,你可以直接使用内置函数。
另一种方式就是使用一对多(one-vs-all)方法。这个我们在讲逻辑回归的时候讨论过,所以,你要做的就是要训练K个SVM,每一个SVM把一个类同其他类区分开。这种操作会给你K个参数向量:
θ(1),θ(2),…,θ(K)
最后,这就与我们在逻辑回归中用到的一对多方法一样,选取使得
(θ(i))Tx
最大的类i即可。
其实大多数软件包都已经内置了多类分类的函数,因此你不必重新造轮子。
1.4.2 逻辑回归 vs SVM
- 如果n(相对于m)大很多时,使用逻辑回归,或者使用无核函数的SVM(线性核函数)。
比如你有一个文本分类的问题,特征数量n=10000,而且如果你的训练集大小为m=10,在这个问题中,你有10000个特征变量,对应10000个词,但是你只有10个训练样本。这种情况下就比较适合使用逻辑回归或者无核函数(线性核函数)的SVM了。 - 如果n较小,m是中等大小,(例如n为1到1000之间的值,m为10到10000之间的值)那么使用高斯核函数的SVM效果好一些。
- 如果n很小,m很大时(例如n=1000,m=100000+),那么高斯核函数的SVM运行起来会很慢,这种情况下,需要尝试手动地创建更多的特征变量,然后使用逻辑回归或者无核函数(线性核函数)的SVM逻辑回归或者无核函数的SVM(线性核函数)**。
逻辑回归和不带核函数的SVM它们都是非常相似的算法,他们会做相似的事情,并且表现也相似,但是根据你实现的具体情况,其中一个可能会比另一个更加有效。
但是SVM的威力会随着你用不同的核函数而发挥出来。
1.4.3 什么时候使用神经网络?
最后,神经网络应该在什么时候使用呢?
对于上面所有的情况,一个设计得很好的神经网络也很可能会非常有效,它的一个缺点(或者说不使用神经网络的原因)是:神经网络训练起来可能会很慢。但是如果你有一个非常好的SVM实现包,它会运行得比较快,比神经网络快很多。
SVM的优化问题,实际上是一个凸优化问题。因此好的SVM优化软件包总是会找到全局最小值,或者接近它的值。
对于SVM,你不需要担心局部最优。在实际应用中,局部最优对神经网络来说不是非常大,但是也不小。所以使用SVM,你不用考虑这部分问题。
1.5 小结
当我遇到机器学习问题时,有时确实不清楚具体使用哪个算法更好,但是正如你在之前的视频中看到的,算法确实很重要,但是通常更重要的是:你有多少数据,你有多熟练,是否擅长做误差分析和调试学习算法,想出如何设计新的特征变量,想出如何设计新的特征变量,以及找出应该输入给学习算法的其它特征变量等方面。通常这些方面会比你使用逻辑回归还是SVM更加重要。
但是SVM仍然被广泛认为是最强大的学习算法之一,最强大的学习算法之一,而且SVM在一个区间内是一个非常有效地学习复杂非线性函数的方法。因此,有了逻辑回归、神经网络、SVM这三个学习算法,我想你已经具备了在广泛的应用里构建最前沿的机器学习系统的能力。