SVD分解在文本分类中的应用


    在自然语言处理中,最常见的两个问题分别是,将文本按主题归类和将词汇按意思归类。这两个问题都可以通过矩阵运算来圆满地,一次次能够解决。首先来看一看余弦定理和新闻分类这个问题

    新闻分类其实就是一个聚类问题,关键是计算两篇新闻的相似程度。问了完成这个任务,我们可以将新闻表示成代表它们内容的实词序列,即向量,然后求两个向量的夹角。夹角越小,表示两篇新闻越相关;当它们垂直正交时,表示两篇新闻无关。从理论上来讲,这种算法非常简单,,也易于实现。但问题是,当我们需要对大量的新闻进行分类时,我们需要两两比较,这需要很多次迭代,因此非常耗时。尤其当新闻数量非常大,同时词汇数量也很大时,这个问题可能会趋于无解。那么我们有没有一种方法,能够一次性地把所有新闻的相关性计算出来呢?答案是肯定的,这就是我们在“线性代数”中学过的SVD(奇异值分解)。

    现在让我们来看看奇异值分解是怎么回事。首先,我们可以用一个大矩阵A来描述这一百万篇文章和五十万词的关联性。这个矩阵中,每一行对应一篇文章,每一列对应一个词。

SVD分解在文本分类中的应用_第1张图片
     在上面的图中,M=1,000,000,N=500,000。第 i 行,第 j 列的元素,是字典中第 j 个词在第 i 篇文章中出现的加权词频(比如,TF/IDF)。读者可能已经注意到了,这个矩阵非常大,有一百万乘以五十万,即五千亿个元素。

    奇异值分解就是把上面这样一个大矩阵,分解成三个小矩阵相乘,如下图所示。比如把上面的例子中的矩阵分解成一个一百万乘以一百的矩阵X,一个一百乘以一百的矩阵B,和一个一百乘以五十万的矩阵Y。这三个矩阵的元素总数加起来也不过1.5亿,仅仅是原来的三千分之一。相应的存储量和计算量都会小三个数量级以上。

SVD分解在文本分类中的应用_第2张图片

    三个矩阵有非常清楚的物理含义。第一个矩阵X是对词进行分类的结果,每一列表示一类主题,其中的每个非零元素表示一个主题与一篇文章的相关性,数值越大越相关。最后一个矩阵Y中的每一列表示100个语义类/词类,每个语义类/词类与500,000个词的相关性。中间的矩阵则表示文章主题和语义类/词类之间的相关性。因此,我们只要对关联矩阵A进行一次奇异值分解,就可以同时完成了近义词分类和文章的分类。(同时得到每类文章和每类词的相关性)。

    接下来,举例说明一下上述三个矩阵:

SVD分解在文本分类中的应用_第3张图片

    X的每一行代表一篇文章,每一列代表一个主题,里边的数值代表文章与主题的相关程度。例如对于第一篇文章,它和第一个主题比较相关,和第二个主题不太相关,第二片文章正好相反;第四篇文章和每一个主题都不太相关,因为其对应的元素(0.3,,0.03)都不大,但相对来说,和第一个主题更相关。


    Y的每一行代表一个语义类,每一列代表一个词,里边的数值代表词与语义类的相关程度。例如对于第一个词,它和第一个语义类相关,与第二个语义类无关;第二个词则相反。

    这里重点关注一下矩阵B,它表示的是主题和语义类/词类之间的相关性,我们可以用一个矩阵来说明:


    在这个矩阵中,第一个主题和第一个语义类相关,和第二个语义类没有太大关系。而第二个主题则相反。

    其实我们可以把矩阵B理解为文章(document)和词汇(word)之间的一个潜在语义项(latent semantics),而X和Y可以理解为同一个潜在语义项对不同文章之间的相关性和不同词之间的相关性的联系。X和Y的大小分别是m*r与r*n,r为A矩阵的rank(秩),最后,B是A的r个奇异值组成的对角方阵(r*r),在谱分解中也就是A的r个特征值。

因此,我们只要对矩阵A进行一次分解,就可以同时完成文章分类和近义词分类,同时还能得到每个主题和每个语义类之间的相关性。这个结果非常漂亮。


     下面看一下SVD在潜在语义索引(Latent Semantic Indexing)中的应用:

SVD分解在文本分类中的应用_第4张图片    这就是一个矩阵,不过不太一样的是,这里的一行表示一个词在哪些title中出现了(一行就是之前说的一维feature),一列表示一个title中有哪些词,(这个矩阵其实是我们之前说的那种一行是一个sample的形式的一种转置,这个会使得我们的左右奇异向量的意义产生变化,但是不会影响我们计算的过程)。比如说T1这个title中就有guide、investing、market、stock四个词,各出现了一次,我们将这个矩阵进行SVD,得到下面的矩阵:

SVD分解在文本分类中的应用_第5张图片    左奇异向量表示词的一些特性,右奇异向量表示文档的一些特性,中间的奇异值矩阵表示左奇异向量的一行与右奇异向量的一列的重要程序,数字越大越重要。

    继续看这个矩阵还可以发现一些有意思的东西,首先,左奇异向量的第一列表示每一个词的出现频繁程度,虽然不是线性的,但是可以认为是一个大概的描述,比如book是0.15对应文档中出现的2次,investing是0.74对应了文档中出现了9次,rich是0.36对应文档中出现了3次;

    其次,右奇异向量中一的第一行表示每一篇文档中的出现词的个数的近似,比如说,T6是0.49,出现了5个词,T2是0.22,出现了2个词。

    然后我们反过头来看,我们可以将左奇异向量和右奇异向量都取后2维(之前是3维的矩阵),投影到一个平面上,可以得到:

SVD分解在文本分类中的应用_第6张图片     在图上,每一个红色的点,都表示一个词,每一个蓝色的点,都表示一篇文档,这样我们可以对这些词和文档进行聚类,比如说stock 和 market可以放在一类,因为他们老是出现在一起,real和estate可以放在一类,dads,guide这种词就看起来有点孤立了,我们就不对他们进行合并了。按这样聚类出现的效果,可以提取文档集合中的近义词,这样当用户检索文档的时候,是用语义级别(近义词集合)去检索了,而不是之前的词的级别。这样一减少我们的检索、存储量,因为这样压缩的文档集合和PCA是异曲同工的,二可以提高我们的用户体验,用户输入一个词,我们可以在这个词的近义词的集合中去找,这是传统的索引无法做到的。



参考资料:

 1)《数学之美》-by 吴军

 2)http://www.cnblogs.com/LeftNotEasy/archive/2011/01/19/svd-and-applications.html(详细介绍了SVD的数学原理)

 3)http://blog.csdn.net/abcjennifer/article/details/8131087

你可能感兴趣的:(算法,机器学习,人工智能,opencv,图像处理)